1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
/*!
Powerful macro for creating iterators on the fly. See [`iterate`] for details.
*/

#![no_std]

use core::fmt;
use core::fmt::Debug;
use core::fmt::Formatter;
use core::iter::FusedIterator;

/**
Create an iterator on the fly

The `iterate` macro creates an iterator on the fly:

```
use iterate::iterate;

let mut iterator = iterate![1, 2, 3];
assert_eq!(iterator.next(), Some(1));
assert_eq!(iterator.next(), Some(2));
assert_eq!(iterator.next(), Some(3));
assert_eq!(iterator.next(), None);
```

The iterator lazily evaluates each of its arguments, one at a time:

```
use std::cell::Cell;
use iterate::iterate;

let cell = Cell::new(0);
let cell = &cell;

let mut iterator = iterate![
    {cell.set(cell.get() + 1); 1},
    {cell.set(cell.get() + 1); 2},
    {cell.set(cell.get() + 1); 3},
];

assert_eq!(cell.get(), 0);
assert_eq!(iterator.next(), Some(1));

assert_eq!(cell.get(), 1);
assert_eq!(iterator.next(), Some(2));

assert_eq!(cell.get(), 2);
assert_eq!(iterator.next(), Some(3));

assert_eq!(cell.get(), 3);
assert_eq!(iterator.next(), None);
```

Most usefully, `iterate` can capture any other [`IntoIterator`] type and
iterate over it, by prefixing the value with `..`:

```
use iterate::iterate;

let range = 0..5;
let vec = vec![4, 1, 2, 3];

// Iterate captures its arguments by move, and evaluates them lazily, so we
// need to ensure that the vec is captured by reference
let vec = &vec;

let iterator = iterate![
    1,
    ..range,
    ..vec.iter().copied(),
    10
];

let result: Vec<i32> = iterator.collect();
assert_eq!(result, [
    1,
    0, 1, 2, 3, 4,
    4, 1, 2, 3,
    10,
])
```

# Eager and Lazy evaluation

`iterate` tries to be smart about when it evaluates its arguments eagerly vs
lazily. In general it tries to evaluate them lazily, but in cases where it's
sure there will be no side effects, it evaluates `..iter` arguments eagerly.
It does this so that it can provide a more reliable `size_hint`.
*/
pub use iterate_proc_macro::iterate;

/// The [`iterate`] macro produces a type that uses unsafe in the
/// implementation. It is therefore critical that users of the library not
/// have access to the fields of the type. Because the type is defined locally,
/// the only way to do this is to wrap it in another type that forwards the
/// iterator implementation
#[derive(Clone, Default)]
#[doc(hidden)]
pub struct ConcealedIterator<I> {
    iter: I,
}

impl<I: Debug> Debug for ConcealedIterator<I> {
    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
        self.iter.fmt(f)
    }
}

impl<I: Iterator> Iterator for ConcealedIterator<I> {
    type Item = I::Item;

    fn next(&mut self) -> Option<Self::Item> {
        self.iter.next()
    }

    fn size_hint(&self) -> (usize, Option<usize>) {
        self.iter.size_hint()
    }
}

impl<I: DoubleEndedIterator> DoubleEndedIterator for ConcealedIterator<I> {
    fn next_back(&mut self) -> Option<Self::Item> {
        self.iter.next_back()
    }
}

impl<I: ExactSizeIterator> ExactSizeIterator for ConcealedIterator<I> {
    fn len(&self) -> usize {
        self.iter.len()
    }
}

impl<I: FusedIterator> FusedIterator for ConcealedIterator<I> {}

#[doc(hidden)]
#[inline]
pub fn conceal<I: Iterator>(iter: I) -> ConcealedIterator<I> {
    ConcealedIterator { iter }
}