iter_builder/
lib.rs

1#![doc = include_str!("../README.md")]
2#![no_std]
3#![allow(non_upper_case_globals, clippy::type_complexity)]
4
5use core::{iter::FusedIterator, marker::PhantomData};
6use traits::*;
7
8pub mod traits;
9
10/// Unimplemented placeholder
11#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Default)]
12pub struct No<T>(PhantomData<T>);
13
14/// Implemented packer
15#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Default)]
16pub struct Meta<F, S, T>(F, PhantomData<(T, S)>);
17
18/// Marker like trait implemented flags
19#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Default)]
20pub struct Flags<
21    const Finish: bool,
22    const Fused: bool,
23    const Exact: bool,
24>;
25
26/// `Iterator` builder
27///
28/// See the [library-level documentation](self) for more.
29#[derive(Debug, Clone)]
30pub struct Iter<
31    S,
32    L,
33    Next,
34    Nth,
35    SizeHint,
36    NextBack,
37    NthBack,
38>
39{
40    pub state: S,
41    next: Next,
42    nth: Nth,
43    size_hint: SizeHint,
44    next_back: NextBack,
45    nth_back: NthBack,
46    flags_phantom: PhantomData<L>,
47}
48
49impl<F, S, T> Iter<
50    S,
51    Flags<false, false, false>,
52    Meta<F, S, T>,
53    No<T>,
54    No<T>,
55    No<T>,
56    No<T>,
57>
58where F: FnMut(&mut S) -> Option<T>,
59{
60    /// Create a [`Iter`] builder
61    ///
62    /// # Examples
63    ///
64    /// ```
65    /// # use iter_builder::Iter;
66    /// let mut iter = Iter::new(0, |i| { *i += 1; Some(*i) }).finish();
67    /// assert_eq!(iter.next(), Some(1));
68    /// assert_eq!(iter.next(), Some(2));
69    /// assert_eq!(iter.next(), Some(3));
70    /// ```
71    pub const fn new(state: S, f: F) -> Self {
72        Self {
73            state,
74            next: Meta(f, PhantomData),
75            nth: No(PhantomData),
76            size_hint: No(PhantomData),
77            next_back: No(PhantomData),
78            nth_back: No(PhantomData),
79            flags_phantom: PhantomData,
80        }
81    }
82}
83
84impl<F, T> Iter<
85    (),
86    Flags<false, false, false>,
87    Meta<F, (), T>,
88    No<T>,
89    No<T>,
90    No<T>,
91    No<T>,
92>
93where F: FnMut(&mut ()) -> Option<T>,
94{
95    /// Create a [`Iter`] builder
96    ///
97    /// # Examples
98    ///
99    /// ```
100    /// # use iter_builder::Iter;
101    /// let mut i = 0;
102    /// let mut iter = Iter::new_unit(|()| { i += 1; Some(i) }).finish();
103    /// assert_eq!(iter.next(), Some(1));
104    /// assert_eq!(iter.next(), Some(2));
105    /// assert_eq!(iter.next(), Some(3));
106    /// assert_eq!(i, 3);
107    /// ```
108    pub const fn new_unit(f: F) -> Self {
109        Self {
110            state: (),
111            next: Meta(f, PhantomData),
112            nth: No(PhantomData),
113            size_hint: No(PhantomData),
114            next_back: No(PhantomData),
115            nth_back: No(PhantomData),
116            flags_phantom: PhantomData,
117        }
118    }
119}
120
121impl<S, const Fused: bool, const Exact: bool, Next, Nth, SizeHint, NextBack, NthBack>
122    Iter<
123        S,
124        Flags<false, Fused, Exact>,
125        Next,
126        Nth,
127        SizeHint,
128        NextBack,
129        NthBack,
130    >
131where Next: IterNext<S>,
132{
133    /// Implement [`Iterator::nth`]
134    ///
135    /// # Examples
136    ///
137    /// ```
138    /// # use iter_builder::Iter;
139    /// let mut iter = Iter::new_unit(|_| Some(1)).nth(|_, _| Some(2)).finish();
140    ///
141    /// assert_eq!(iter.next(), Some(1));
142    /// assert_eq!(iter.next(), Some(1));
143    /// assert_eq!(iter.nth(0), Some(2));
144    /// assert_eq!(iter.nth(1), Some(2));
145    /// ```
146    pub fn nth<F>(self, f: F) -> Iter<
147        S,
148        Flags<false, Fused, Exact>,
149        Next,
150        Meta<F, S, Next::T>,
151        SizeHint,
152        NextBack,
153        NthBack,
154    >
155    where F: FnMut(&mut S, usize) -> Option<Next::T>,
156          Nth: Unimplemented,
157    {
158        let Self {
159            state,
160            next,
161            nth: _,
162            size_hint,
163            next_back,
164            nth_back,
165            flags_phantom,
166        } = self;
167        let nth = Meta(f, PhantomData);
168
169        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom }
170    }
171
172    /// Implement [`Iterator::size_hint`]
173    ///
174    /// # Examples
175    ///
176    /// ```
177    /// # use iter_builder::Iter;
178    /// let mut iter = Iter::new_unit(|_| Some(1)).size_hint(|_| (2333, None)).finish();
179    ///
180    /// assert_eq!(iter.size_hint(), (2333, None));
181    /// ```
182    pub fn size_hint<F>(self, f: F) -> Iter<
183        S,
184        Flags<false, Fused, Exact>,
185        Next,
186        Nth,
187        Meta<F, S, Next::T>,
188        NextBack,
189        NthBack,
190    >
191    where F: Fn(&S) -> (usize, Option<usize>),
192          SizeHint: Unimplemented,
193    {
194        let Self {
195            state,
196            next,
197            nth,
198            size_hint: _,
199            next_back,
200            nth_back,
201            flags_phantom,
202        } = self;
203        let size_hint = Meta(f, PhantomData);
204
205        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom }
206    }
207
208    /// Implement [`DoubleEndedIterator`] and [`DoubleEndedIterator::next_back`]
209    ///
210    /// # Examples
211    ///
212    /// ```
213    /// # use iter_builder::Iter;
214    /// let mut iter = Iter::new_unit(|_| Some(1)).next_back(|_| Some(3)).finish();
215    ///
216    /// assert_eq!(iter.next(), Some(1));
217    /// assert_eq!(iter.next(), Some(1));
218    /// assert_eq!(iter.next_back(), Some(3));
219    /// assert_eq!(iter.next_back(), Some(3));
220    /// ```
221    pub fn next_back<F>(self, f: F) -> Iter<
222        S,
223        Flags<false, Fused, Exact>,
224        Next,
225        Nth,
226        SizeHint,
227        Meta<F, S, Next::T>,
228        NthBack,
229    >
230    where F: FnMut(&mut S) -> Option<Next::T>,
231          NextBack: Unimplemented,
232    {
233        let Self {
234            state,
235            next,
236            nth,
237            size_hint,
238            next_back: _,
239            nth_back,
240            flags_phantom,
241        } = self;
242        let next_back = Meta(f, PhantomData);
243
244        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom }
245    }
246
247    /// Implement [`DoubleEndedIterator::nth_back`]
248    ///
249    /// # Examples
250    ///
251    /// ```
252    /// # use iter_builder::Iter;
253    /// let mut iter = Iter::new_unit(|_| todo!())
254    ///     .next_back(|_| todo!())
255    ///     .nth_back(|_, _| Some(2))
256    ///     .finish();
257    ///
258    /// assert_eq!(iter.nth_back(0), Some(2));
259    /// assert_eq!(iter.nth_back(1), Some(2));
260    /// ```
261    pub fn nth_back<F>(self, f: F) -> Iter<
262        S,
263        Flags<false, Fused, Exact>,
264        Next,
265        Nth,
266        SizeHint,
267        NextBack,
268        Meta<F, S, Next::T>,
269    >
270    where F: FnMut(&mut S, usize) -> Option<Next::T>,
271          NthBack: Unimplemented,
272    {
273        let Self {
274            state,
275            next,
276            nth,
277            size_hint,
278            next_back,
279            nth_back: _,
280            flags_phantom,
281        } = self;
282        let nth_back = Meta(f, PhantomData);
283
284        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom }
285    }
286
287    /// Implement [`ExactSizeIterator`]
288    pub fn exact(self) -> Iter<
289        S,
290        Flags<false, Fused, true>,
291        Next,
292        Nth,
293        SizeHint,
294        NextBack,
295        NthBack,
296    >
297    where Predicate<Exact>: Unimplemented,
298    {
299        let Self {
300            state,
301            next,
302            nth,
303            size_hint,
304            next_back,
305            nth_back,
306            flags_phantom: _,
307        } = self;
308
309        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom: PhantomData }
310    }
311
312    /// Implement [`FusedIterator`]
313    pub fn fused(self) -> Iter<
314        S,
315        Flags<false, true, Exact>,
316        Next,
317        Nth,
318        SizeHint,
319        NextBack,
320        NthBack,
321    >
322    where Predicate<Fused>: Unimplemented,
323    {
324        let Self {
325            state,
326            next,
327            nth,
328            size_hint,
329            next_back,
330            nth_back,
331            flags_phantom: _,
332        } = self;
333
334        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom: PhantomData }
335    }
336
337    /// Generate output [`Iterator`]
338    pub fn finish(self) -> Iter<
339        S,
340        Flags<true, Fused, Exact>,
341        Next,
342        Nth,
343        SizeHint,
344        NextBack,
345        NthBack,
346    > {
347        let Self {
348            state,
349            next,
350            nth,
351            size_hint,
352            next_back,
353            nth_back,
354            flags_phantom: _,
355        } = self;
356
357        Iter { state, next, nth, size_hint, next_back, nth_back, flags_phantom: PhantomData }
358    }
359}
360
361impl<S, const Fused: bool, const Exact: bool, Next, Nth, SizeHint, NextBack, NthBack>
362    Iterator
363    for Iter<
364        S,
365        Flags<true, Fused, Exact>,
366        Next,
367        Nth,
368        SizeHint,
369        NextBack,
370        NthBack,
371    >
372where Next: IterNext<S>,
373      Nth: IterNth<S, T = Next::T>,
374      SizeHint: IterSizeHint<S>
375{
376    type Item = Next::T;
377
378    fn next(&mut self) -> Option<Self::Item> {
379        self.next.iter_next(&mut self.state)
380    }
381
382    fn nth(&mut self, n: usize) -> Option<Self::Item> {
383        self.nth.iter_nth(&mut self.state, &mut self.next, n)
384    }
385
386    fn size_hint(&self) -> (usize, Option<usize>) {
387        self.size_hint.iter_size_hint(&self.state)
388    }
389}
390
391impl<S, const Fused: bool, const Exact: bool, Next, Nth, SizeHint, NextBack, NthBack>
392    DoubleEndedIterator
393    for Iter<
394        S,
395        Flags<true, Fused, Exact>,
396        Next,
397        Nth,
398        SizeHint,
399        NextBack,
400        NthBack,
401    >
402where Next: IterNext<S>,
403      Nth: IterNth<S, T = Next::T>,
404      SizeHint: IterSizeHint<S>,
405      NextBack: IterNextBack<S, T = Next::T>,
406      NthBack: IterNthBack<S, T = Next::T>,
407{
408    fn next_back(&mut self) -> Option<Self::Item> {
409        self.next_back.iter_next_back(&mut self.state)
410    }
411
412    fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
413        self.nth_back.iter_nth_back(&mut self.state, &mut self.next_back, n)
414    }
415}
416
417impl<S, const Exact: bool, Next, Nth, SizeHint, NextBack, NthBack>
418    FusedIterator
419    for Iter<
420        S,
421        Flags<true, true, Exact>,
422        Next,
423        Nth,
424        SizeHint,
425        NextBack,
426        NthBack,
427    >
428where Next: IterNext<S>,
429      Nth: IterNth<S, T = Next::T>,
430      SizeHint: IterSizeHint<S>,
431{
432}
433
434impl<S, const Fused: bool, Next, Nth, SizeHint, NextBack, NthBack>
435    ExactSizeIterator
436    for Iter<
437        S,
438        Flags<true, Fused, true>,
439        Next,
440        Nth,
441        SizeHint,
442        NextBack,
443        NthBack,
444    >
445where Next: IterNext<S>,
446      Nth: IterNth<S, T = Next::T>,
447      SizeHint: IterSizeHint<S> + Implemented,
448{
449}
450
451#[cfg(test)]
452mod tests {
453    use super::*;
454
455    #[test]
456    fn test_next() {
457        let mut iter = Iter::new(0, |n| {
458            let i = *n;
459            (i < 3).then_some(())?;
460            *n += 1;
461            Some(i)
462        }).finish();
463        assert_eq!(iter.next(), Some(0));
464        assert_eq!(iter.next(), Some(1));
465        assert_eq!(iter.next(), Some(2));
466        assert_eq!(iter.next(), None);
467    }
468
469    #[test]
470    fn test_nth() {
471        let mut iter = Iter::new(0, |n| {
472            let i = *n;
473            (i < 3).then_some(())?;
474            *n += 1;
475            Some(i)
476        }).nth(|_, n| Some(n)).finish();
477        assert_eq!(iter.next(), Some(0));
478        assert_eq!(iter.next(), Some(1));
479        assert_eq!(iter.next(), Some(2));
480        assert_eq!(iter.next(), None);
481        assert_eq!(iter.nth(0), Some(0));
482        assert_eq!(iter.nth(9), Some(9));
483    }
484
485    #[test]
486    fn test_nth_dep() {
487        let mut iter = Iter::new(0, |n| {
488            let i = *n;
489            (i < 3).then_some(())?;
490            *n += 1;
491            Some(i)
492        }).finish();
493        assert_eq!(iter.nth(0), Some(0));
494        assert_eq!(iter.nth(1), Some(2));
495        assert_eq!(iter.nth(0), None);
496    }
497
498    #[test]
499    fn test_size_hint() {
500        let mut iter = Iter::new(0, |n| {
501            let i = *n;
502            (i < 3).then_some(())?;
503            *n += 1;
504            Some(i)
505        }).size_hint(|s| (3-s, Some(3-s))).finish();
506        assert_eq!(iter.size_hint(), (3, Some(3)));
507        assert_eq!(iter.next(), Some(0));
508        assert_eq!(iter.size_hint(), (2, Some(2)));
509        assert_eq!(iter.next(), Some(1));
510        assert_eq!(iter.next(), Some(2));
511        assert_eq!(iter.next(), None);
512        assert_eq!(iter.size_hint(), (0, Some(0)));
513        assert_eq!(iter.next(), None);
514        assert_eq!(iter.size_hint(), (0, Some(0)));
515    }
516
517    #[test]
518    fn test_exact() {
519        let mut iter = Iter::new(0, |n| {
520            let i = *n;
521            (i < 3).then_some(())?;
522            *n += 1;
523            Some(i)
524        }).size_hint(|s| (3-s, Some(3-s))).exact().finish();
525        assert_eq!(iter.len(), 3);
526        assert_eq!(iter.next(), Some(0));
527        assert_eq!(iter.len(), 2);
528        assert_eq!(iter.next(), Some(1));
529        assert_eq!(iter.next(), Some(2));
530        assert_eq!(iter.len(), 0);
531        assert_eq!(iter.next(), None);
532        assert_eq!(iter.len(), 0);
533    }
534
535    #[test]
536    fn test_fused() {
537        let mut iter = Iter::new(0, |n| {
538            let i = *n;
539            (i < 3).then_some(())?;
540            *n += 1;
541            Some(i)
542        }).fused().finish();
543        assert_eq!(iter.next(), Some(0));
544        assert_eq!(iter.next(), Some(1));
545        assert_eq!(iter.next(), Some(2));
546        assert_eq!(iter.next(), None);
547    }
548
549    #[test]
550    fn test_exact_fused() {
551        let mut iter = Iter::new(0, |n| {
552            let i = *n;
553            (i < 3).then_some(())?;
554            *n += 1;
555            Some(i)
556        }).exact().fused().finish();
557        assert_eq!(iter.next(), Some(0));
558        assert_eq!(iter.next(), Some(1));
559        assert_eq!(iter.next(), Some(2));
560        assert_eq!(iter.next(), None);
561    }
562
563    #[test]
564    fn test_next_back() {
565        let mut iter = Iter::new((0, 3), |(a, b)| {
566            let i = *a;
567            (i < *b).then_some(())?;
568            *a += 1;
569            Some(i)
570        }).next_back(|(a, b)| {
571            (*a < *b).then_some(())?;
572            *b -= 1;
573            Some(*b)
574        }).finish();
575        let mut iter1 = iter.clone();
576        assert_eq!(iter.next(), Some(0));
577        assert_eq!(iter.next(), Some(1));
578        assert_eq!(iter.next(), Some(2));
579        assert_eq!(iter.next(), None);
580
581        assert_eq!(iter1.next(), Some(0));
582        assert_eq!(iter1.next_back(), Some(2));
583        assert_eq!(iter1.next_back(), Some(1));
584        assert_eq!(iter1.next_back(), None);
585        assert_eq!(iter1.next(), None);
586    }
587
588    #[test]
589    fn size() {
590        let f = |_: &mut ()| Some(());
591        assert_eq!(size_of_val(&f), 0);
592        let iter = Iter::new((), f);
593        assert_eq!(size_of_val(&iter), 0);
594        let mut iter = iter.finish();
595        assert_eq!(size_of_val(&iter), 0);
596        assert_eq!(iter.next(), Some(()));
597    }
598
599    #[test]
600    fn size1() {
601        let f = |_: &mut ()| Some(());
602        assert_eq!(size_of_val(&f), 0);
603        let iter = Iter::new((), f).next_back(f);
604        assert_eq!(size_of_val(&iter), 0);
605        let mut iter = iter.finish();
606        assert_eq!(size_of_val(&iter), 0);
607        assert_eq!(iter.next(), Some(()));
608        assert_eq!(iter.next_back(), Some(()));
609    }
610}