rust_queries_core/
lock_lazy.rs1use crate::locks::LockValue;
6use key_paths_core::KeyPaths;
7use std::marker::PhantomData;
8
9pub struct LockLazyQuery<'a, T: 'static, L, I>
11where
12 L: LockValue<T> + 'a,
13 I: Iterator<Item = &'a L>,
14{
15 iter: I,
16 _phantom: PhantomData<&'a T>,
17}
18
19impl<'a, T: 'static, L, I> LockLazyQuery<'a, T, L, I>
20where
21 L: LockValue<T> + 'a,
22 I: Iterator<Item = &'a L> + 'a,
23{
24 pub fn new(iter: I) -> Self {
26 Self {
27 iter,
28 _phantom: PhantomData,
29 }
30 }
31
32 pub fn where_<F, P>(self, path: KeyPaths<T, F>, predicate: P) -> LockLazyQuery<'a, T, L, impl Iterator<Item = &'a L> + 'a>
34 where
35 F: 'static,
36 P: Fn(&F) -> bool + 'a,
37 {
38 LockLazyQuery {
39 iter: self.iter.filter(move |lock| {
40 lock.with_value(|item| {
41 path.get(item).map_or(false, |val| predicate(val))
42 })
43 .unwrap_or(false)
44 }),
45 _phantom: PhantomData,
46 }
47 }
48
49 pub fn select_lazy<F>(self, path: KeyPaths<T, F>) -> impl Iterator<Item = F> + 'a
51 where
52 F: Clone + 'static,
53 {
54 self.iter.filter_map(move |lock| {
55 lock.with_value(|item| path.get(item).cloned()).flatten()
56 })
57 }
58
59 pub fn take_lazy(self, n: usize) -> impl Iterator<Item = T> + 'a
61 where
62 T: Clone,
63 {
64 self.iter
65 .filter_map(|lock| lock.with_value(|item| item.clone()))
66 .take(n)
67 }
68
69 pub fn skip_lazy(self, n: usize) -> LockLazyQuery<'a, T, L, impl Iterator<Item = &'a L> + 'a> {
71 LockLazyQuery {
72 iter: self.iter.skip(n),
73 _phantom: PhantomData,
74 }
75 }
76
77 pub fn count(self) -> usize {
79 self.iter.count()
80 }
81
82 pub fn first(mut self) -> Option<T>
84 where
85 T: Clone,
86 {
87 self.iter
88 .find_map(|lock| lock.with_value(|item| item.clone()))
89 }
90
91 pub fn any(mut self) -> bool {
93 self.iter.next().is_some()
94 }
95
96 pub fn collect(self) -> Vec<T>
98 where
99 T: Clone,
100 {
101 self.iter
102 .filter_map(|lock| lock.with_value(|item| item.clone()))
103 .collect()
104 }
105}
106