1use super::*;
4use std::collections::VecDeque;
5
6mod _triple {
7 use super::*;
8 use triple::Triple;
9
10 pub struct FilterMapTripleSource<S, F> {
12 pub(in super::super) source: S,
13 pub(in super::super) filter_map: F,
14 }
15
16 impl<S, F, T> TripleSource for FilterMapTripleSource<S, F>
17 where
18 S: TripleSource,
19 F: FnMut(S::Triple<'_>) -> Option<T>,
20 T: Triple,
21 {
22 type Triple<'x> = T;
23 type Error = S::Error;
24
25 fn try_for_some_triple<E, F2>(&mut self, mut f: F2) -> StreamResult<bool, Self::Error, E>
26 where
27 E: Error,
28 F2: FnMut(Self::Triple<'_>) -> Result<(), E>,
29 {
30 let filter_map = &mut self.filter_map;
31 self.source.try_for_some_triple(|t| match (filter_map)(t) {
32 None => Ok(()),
33 Some(out) => f(out),
34 })
35 }
36
37 fn size_hint_triples(&self) -> (usize, Option<usize>) {
38 (0, self.source.size_hint_triples().1)
39 }
40 }
41
42 impl<S, F, T> QuadSource for FilterMapTripleSource<S, F>
43 where
44 S: TripleSource,
45 F: FnMut(S::Triple<'_>) -> Option<T>,
46 T: crate::quad::Quad,
47 {
48 type Quad<'x> = T;
49 type Error = S::Error;
50
51 fn try_for_some_quad<E, F2>(&mut self, mut f: F2) -> StreamResult<bool, Self::Error, E>
52 where
53 E: Error,
54 F2: FnMut(Self::Quad<'_>) -> Result<(), E>,
55 {
56 let filter_map = &mut self.filter_map;
57 self.source.try_for_some_triple(|t| match (filter_map)(t) {
58 None => Ok(()),
59 Some(out) => f(out),
60 })
61 }
62
63 fn size_hint_quads(&self) -> (usize, Option<usize>) {
64 (0, self.source.size_hint_triples().1)
65 }
66 }
67
68 impl<S, F, T> IntoIterator for FilterMapTripleSource<S, F>
69 where
70 S: TripleSource,
71 F: FnMut(S::Triple<'_>) -> Option<T>,
72 {
73 type Item = Result<T, S::Error>;
74 type IntoIter = FilterMapTripleSourceIterator<S, F, T, S::Error>;
75
76 fn into_iter(self) -> Self::IntoIter {
77 FilterMapTripleSourceIterator {
78 source: self.source,
79 filter_map: self.filter_map,
80 buffer: VecDeque::new(),
81 }
82 }
83 }
84
85 pub struct FilterMapTripleSourceIterator<S, F, T, E> {
87 source: S,
88 filter_map: F,
89 buffer: VecDeque<Result<T, E>>,
90 }
91
92 impl<S, F, T> Iterator for FilterMapTripleSourceIterator<S, F, T, S::Error>
93 where
94 S: TripleSource,
95 F: FnMut(S::Triple<'_>) -> Option<T>,
96 {
97 type Item = Result<T, S::Error>;
98 fn next(&mut self) -> Option<Result<T, S::Error>> {
99 let mut remaining = true;
100 let mut buffer = VecDeque::new();
101 std::mem::swap(&mut self.buffer, &mut buffer);
102 while buffer.is_empty() && remaining {
103 match self.source.for_some_triple(&mut |i| {
104 if let Some(t) = (self.filter_map)(i) {
105 buffer.push_back(Ok(t));
106 }
107 }) {
108 Ok(b) => {
109 remaining = b;
110 }
111 Err(err) => {
112 buffer.push_back(Err(err));
113 remaining = false;
114 }
115 }
116 }
117 std::mem::swap(&mut self.buffer, &mut buffer);
118 self.buffer.pop_front()
119 }
120
121 fn size_hint(&self) -> (usize, Option<usize>) {
122 self.source.size_hint_triples()
123 }
124 }
125}
126pub use _triple::*;
127
128mod _quad {
135 use super::*;
136 use quad::Quad;
137
138 pub struct FilterMapQuadSource<S, F> {
140 pub(in super::super) source: S,
141 pub(in super::super) filter_map: F,
142 }
143
144 impl<S, F, T> QuadSource for FilterMapQuadSource<S, F>
145 where
146 S: QuadSource,
147 F: FnMut(S::Quad<'_>) -> Option<T>,
148 T: Quad,
149 {
150 type Quad<'x> = T;
151 type Error = S::Error;
152
153 fn try_for_some_quad<E, F2>(&mut self, mut f: F2) -> StreamResult<bool, Self::Error, E>
154 where
155 E: Error,
156 F2: FnMut(Self::Quad<'_>) -> Result<(), E>,
157 {
158 let filter_map = &mut self.filter_map;
159 self.source.try_for_some_quad(|t| match (filter_map)(t) {
160 None => Ok(()),
161 Some(out) => f(out),
162 })
163 }
164
165 fn size_hint_quads(&self) -> (usize, Option<usize>) {
166 (0, self.source.size_hint_quads().1)
167 }
168 }
169
170 impl<S, F, T> TripleSource for FilterMapQuadSource<S, F>
171 where
172 S: QuadSource,
173 F: FnMut(S::Quad<'_>) -> Option<T>,
174 T: crate::triple::Triple,
175 {
176 type Triple<'x> = T;
177 type Error = S::Error;
178
179 fn try_for_some_triple<E, F2>(&mut self, mut f: F2) -> StreamResult<bool, Self::Error, E>
180 where
181 E: Error,
182 F2: FnMut(Self::Triple<'_>) -> Result<(), E>,
183 {
184 let filter_map = &mut self.filter_map;
185 self.source.try_for_some_quad(|t| match (filter_map)(t) {
186 None => Ok(()),
187 Some(out) => f(out),
188 })
189 }
190
191 fn size_hint_triples(&self) -> (usize, Option<usize>) {
192 (0, self.source.size_hint_quads().1)
193 }
194 }
195
196 impl<S, F, T> IntoIterator for FilterMapQuadSource<S, F>
197 where
198 S: QuadSource,
199 F: FnMut(S::Quad<'_>) -> Option<T>,
200 {
201 type Item = Result<T, S::Error>;
202 type IntoIter = FilterMapQuadSourceIterator<S, F, T, S::Error>;
203
204 fn into_iter(self) -> Self::IntoIter {
205 FilterMapQuadSourceIterator {
206 source: self.source,
207 filter_map: self.filter_map,
208 buffer: VecDeque::new(),
209 }
210 }
211 }
212
213 pub struct FilterMapQuadSourceIterator<S, F, T, E> {
215 source: S,
216 filter_map: F,
217 buffer: VecDeque<Result<T, E>>,
218 }
219
220 impl<S, F, T> Iterator for FilterMapQuadSourceIterator<S, F, T, S::Error>
221 where
222 S: QuadSource,
223 F: FnMut(S::Quad<'_>) -> Option<T>,
224 {
225 type Item = Result<T, S::Error>;
226 fn next(&mut self) -> Option<Result<T, S::Error>> {
227 let mut remaining = true;
228 let mut buffer = VecDeque::new();
229 std::mem::swap(&mut self.buffer, &mut buffer);
230 while buffer.is_empty() && remaining {
231 match self.source.for_some_quad(&mut |i| {
232 if let Some(t) = (self.filter_map)(i) {
233 buffer.push_back(Ok(t));
234 }
235 }) {
236 Ok(b) => {
237 remaining = b;
238 }
239 Err(err) => {
240 buffer.push_back(Err(err));
241 remaining = false;
242 }
243 }
244 }
245 std::mem::swap(&mut self.buffer, &mut buffer);
246 self.buffer.pop_front()
247 }
248
249 fn size_hint(&self) -> (usize, Option<usize>) {
250 self.source.size_hint_quads()
251 }
252 }
253}
254pub use _quad::*;
255
256#[cfg(test)]
257mod test {
258 use super::*;
259 use crate::dataset::{Dataset, MutableDataset};
260 use crate::graph::{Graph, MutableGraph};
261 use crate::quad::{Quad, Spog};
262 use crate::term::ez_term;
263 use crate::term::{SimpleTerm, Term};
264 use crate::triple::Triple;
265
266 #[test]
270 fn ts_filter_map_to_triples() {
271 let g = vec![
272 [ez_term(":a"), ez_term(":b"), ez_term(":c")],
273 [ez_term(":d"), ez_term(":e"), ez_term(":f")],
274 [ez_term(":g"), ez_term(":h"), ez_term(":i")],
275 ];
276 let mut h: Vec<[SimpleTerm; 3]> = vec![];
277 g.triples()
278 .filter_map_triples(|t| {
279 (!Term::eq(t.p(), ez_term(":e"))).then_some([t.o(), t.p(), t.s()])
280 })
281 .for_each_triple(|t| {
282 h.insert_triple(t).unwrap();
283 })
284 .unwrap();
285 assert_eq!(
286 h,
287 vec![
288 [ez_term(":c"), ez_term(":b"), ez_term(":a")],
289 [ez_term(":i"), ez_term(":h"), ez_term(":g")],
290 ]
291 )
292 }
293
294 #[test]
295 fn ts_filter_map_to_quads() {
296 let g = vec![
297 [ez_term(":a"), ez_term(":b"), ez_term(":c")],
298 [ez_term(":g"), ez_term(":h"), ez_term(":i")],
299 ];
300 let mut h: Vec<Spog<SimpleTerm>> = vec![];
301 g.triples()
302 .filter_map_triples(|t| {
303 (!Term::eq(t.p(), ez_term(":e"))).then_some(([t.o(), t.p(), t.s()], None))
304 })
305 .for_each_quad(|q| {
306 h.insert_quad(q).unwrap();
307 })
308 .unwrap();
309 assert_eq!(
310 h,
311 vec![
312 ([ez_term(":c"), ez_term(":b"), ez_term(":a")], None),
313 ([ez_term(":i"), ez_term(":h"), ez_term(":g")], None),
314 ]
315 )
316 }
317
318 #[test]
319 fn ts_filter_map_iter() {
320 let g = vec![
321 [ez_term(":a"), ez_term(":b"), ez_term(":c")],
322 [ez_term(":d"), ez_term(":e"), ez_term(":f")],
323 [ez_term(":g"), ez_term(":h"), ez_term(":i")],
324 ];
325 let h: Result<Vec<String>, _> = g
326 .triples()
327 .filter_map_triples(|t| {
328 (!Term::eq(t.p(), ez_term(":e"))).then_some(t.s().iri().unwrap().to_string())
329 })
330 .into_iter()
331 .collect();
332 assert_eq!(h.unwrap(), vec!["tag:a".to_string(), "tag:g".to_string(),])
333 }
334
335 #[test]
339 fn qs_filter_map_to_triples() {
340 let d = vec![
341 ([ez_term(":a"), ez_term(":b"), ez_term(":c")], None),
342 ([ez_term(":d"), ez_term(":e"), ez_term(":f")], None),
343 ([ez_term(":g"), ez_term(":h"), ez_term(":i")], None),
344 ];
345 let mut h: Vec<[SimpleTerm; 3]> = vec![];
346 d.quads()
347 .filter_map_quads(|q| {
348 (!Term::eq(q.p(), ez_term(":e"))).then_some([q.o(), q.p(), q.s()])
349 })
350 .for_each_triple(|t| {
351 h.insert_triple(t).unwrap();
352 })
353 .unwrap();
354 assert_eq!(
355 h,
356 vec![
357 [ez_term(":c"), ez_term(":b"), ez_term(":a")],
358 [ez_term(":i"), ez_term(":h"), ez_term(":g")],
359 ]
360 )
361 }
362
363 #[test]
364 fn qs_filter_map_to_quads() {
365 let d = vec![
366 ([ez_term(":a"), ez_term(":b"), ez_term(":c")], None),
367 ([ez_term(":d"), ez_term(":e"), ez_term(":f")], None),
368 ([ez_term(":g"), ez_term(":h"), ez_term(":i")], None),
369 ];
370 let mut h: Vec<Spog<SimpleTerm>> = vec![];
371 d.quads()
372 .filter_map_quads(|q| {
373 (!Term::eq(q.p(), ez_term(":e"))).then_some(([q.o(), q.p(), q.s()], q.g()))
374 })
375 .for_each_quad(|q| {
376 h.insert_quad(q).unwrap();
377 })
378 .unwrap();
379 assert_eq!(
380 h,
381 vec![
382 ([ez_term(":c"), ez_term(":b"), ez_term(":a")], None),
383 ([ez_term(":i"), ez_term(":h"), ez_term(":g")], None),
384 ]
385 )
386 }
387
388 #[test]
389 fn qs_filter_map_iter() {
390 let d = vec![
391 ([ez_term(":a"), ez_term(":b"), ez_term(":c")], None),
392 ([ez_term(":d"), ez_term(":e"), ez_term(":f")], None),
393 ([ez_term(":g"), ez_term(":h"), ez_term(":i")], None),
394 ];
395 let h: Result<Vec<String>, _> = d
396 .quads()
397 .filter_map_quads(|q| {
398 (!Term::eq(q.p(), ez_term(":e"))).then_some(q.s().iri().unwrap().to_string())
399 })
400 .into_iter()
401 .collect();
402 assert_eq!(h.unwrap(), vec!["tag:a".to_string(), "tag:g".to_string(),])
403 }
404}