1 use crate::iter
::adapters
::{zip::try_get_unchecked, SourceIter, TrustedRandomAccess}
;
2 use crate::iter
::{FusedIterator, InPlaceIterable, TrustedLen}
;
5 /// An iterator that yields the current count and the element during iteration.
7 /// This `struct` is created by the [`enumerate`] method on [`Iterator`]. See its
8 /// documentation for more.
10 /// [`enumerate`]: Iterator::enumerate
11 /// [`Iterator`]: trait.Iterator.html
12 #[derive(Clone, Debug)]
13 #[must_use = "iterators are lazy and do nothing unless consumed"]
14 #[stable(feature = "rust1", since = "1.0.0")]
15 pub struct Enumerate
<I
> {
19 impl<I
> Enumerate
<I
> {
20 pub(in crate::iter
) fn new(iter
: I
) -> Enumerate
<I
> {
21 Enumerate { iter, count: 0 }
25 #[stable(feature = "rust1", since = "1.0.0")]
26 impl<I
> Iterator
for Enumerate
<I
>
30 type Item
= (usize, <I
as Iterator
>::Item
);
32 /// # Overflow Behavior
34 /// The method does no guarding against overflows, so enumerating more than
35 /// `usize::MAX` elements either produces the wrong result or panics. If
36 /// debug assertions are enabled, a panic is guaranteed.
40 /// Might panic if the index of the element overflows a `usize`.
42 #[rustc_inherit_overflow_checks]
43 fn next(&mut self) -> Option
<(usize, <I
as Iterator
>::Item
)> {
44 let a
= self.iter
.next()?
;
51 fn size_hint(&self) -> (usize, Option
<usize>) {
56 #[rustc_inherit_overflow_checks]
57 fn nth(&mut self, n
: usize) -> Option
<(usize, I
::Item
)> {
58 let a
= self.iter
.nth(n
)?
;
59 let i
= self.count
+ n
;
65 fn count(self) -> usize {
70 fn try_fold
<Acc
, Fold
, R
>(&mut self, init
: Acc
, fold
: Fold
) -> R
73 Fold
: FnMut(Acc
, Self::Item
) -> R
,
77 fn enumerate
<'a
, T
, Acc
, R
>(
79 mut fold
: impl FnMut(Acc
, (usize, T
)) -> R
+ 'a
,
80 ) -> impl FnMut(Acc
, T
) -> R
+ 'a
{
81 #[rustc_inherit_overflow_checks]
83 let acc
= fold(acc
, (*count
, item
));
89 self.iter
.try_fold(init
, enumerate(&mut self.count
, fold
))
93 fn fold
<Acc
, Fold
>(self, init
: Acc
, fold
: Fold
) -> Acc
95 Fold
: FnMut(Acc
, Self::Item
) -> Acc
,
100 mut fold
: impl FnMut(Acc
, (usize, T
)) -> Acc
,
101 ) -> impl FnMut(Acc
, T
) -> Acc
{
102 #[rustc_inherit_overflow_checks]
104 let acc
= fold(acc
, (count
, item
));
110 self.iter
.fold(init
, enumerate(self.count
, fold
))
113 #[rustc_inherit_overflow_checks]
114 unsafe fn __iterator_get_unchecked(&mut self, idx
: usize) -> <Self as Iterator
>::Item
116 Self: TrustedRandomAccess
,
118 // SAFETY: the caller must uphold the contract for
119 // `Iterator::__iterator_get_unchecked`.
120 let value
= unsafe { try_get_unchecked(&mut self.iter, idx) }
;
121 (self.count
+ idx
, value
)
125 #[stable(feature = "rust1", since = "1.0.0")]
126 impl<I
> DoubleEndedIterator
for Enumerate
<I
>
128 I
: ExactSizeIterator
+ DoubleEndedIterator
,
131 fn next_back(&mut self) -> Option
<(usize, <I
as Iterator
>::Item
)> {
132 let a
= self.iter
.next_back()?
;
133 let len
= self.iter
.len();
134 // Can safely add, `ExactSizeIterator` promises that the number of
135 // elements fits into a `usize`.
136 Some((self.count
+ len
, a
))
140 fn nth_back(&mut self, n
: usize) -> Option
<(usize, <I
as Iterator
>::Item
)> {
141 let a
= self.iter
.nth_back(n
)?
;
142 let len
= self.iter
.len();
143 // Can safely add, `ExactSizeIterator` promises that the number of
144 // elements fits into a `usize`.
145 Some((self.count
+ len
, a
))
149 fn try_rfold
<Acc
, Fold
, R
>(&mut self, init
: Acc
, fold
: Fold
) -> R
152 Fold
: FnMut(Acc
, Self::Item
) -> R
,
155 // Can safely add and subtract the count, as `ExactSizeIterator` promises
156 // that the number of elements fits into a `usize`.
157 fn enumerate
<T
, Acc
, R
>(
159 mut fold
: impl FnMut(Acc
, (usize, T
)) -> R
,
160 ) -> impl FnMut(Acc
, T
) -> R
{
163 fold(acc
, (count
, item
))
167 let count
= self.count
+ self.iter
.len();
168 self.iter
.try_rfold(init
, enumerate(count
, fold
))
172 fn rfold
<Acc
, Fold
>(self, init
: Acc
, fold
: Fold
) -> Acc
174 Fold
: FnMut(Acc
, Self::Item
) -> Acc
,
176 // Can safely add and subtract the count, as `ExactSizeIterator` promises
177 // that the number of elements fits into a `usize`.
178 fn enumerate
<T
, Acc
>(
180 mut fold
: impl FnMut(Acc
, (usize, T
)) -> Acc
,
181 ) -> impl FnMut(Acc
, T
) -> Acc
{
184 fold(acc
, (count
, item
))
188 let count
= self.count
+ self.iter
.len();
189 self.iter
.rfold(init
, enumerate(count
, fold
))
193 #[stable(feature = "rust1", since = "1.0.0")]
194 impl<I
> ExactSizeIterator
for Enumerate
<I
>
196 I
: ExactSizeIterator
,
198 fn len(&self) -> usize {
202 fn is_empty(&self) -> bool
{
208 #[unstable(feature = "trusted_random_access", issue = "none")]
209 unsafe impl<I
> TrustedRandomAccess
for Enumerate
<I
>
211 I
: TrustedRandomAccess
,
213 const MAY_HAVE_SIDE_EFFECT
: bool
= I
::MAY_HAVE_SIDE_EFFECT
;
216 #[stable(feature = "fused", since = "1.26.0")]
217 impl<I
> FusedIterator
for Enumerate
<I
> where I
: FusedIterator {}
219 #[unstable(feature = "trusted_len", issue = "37572")]
220 unsafe impl<I
> TrustedLen
for Enumerate
<I
> where I
: TrustedLen {}
222 #[unstable(issue = "none", feature = "inplace_iteration")]
223 unsafe impl<S
: Iterator
, I
: Iterator
> SourceIter
for Enumerate
<I
>
225 I
: SourceIter
<Source
= S
>,
230 unsafe fn as_inner(&mut self) -> &mut S
{
231 // SAFETY: unsafe function forwarding to unsafe function with the same requirements
232 unsafe { SourceIter::as_inner(&mut self.iter) }
236 #[unstable(issue = "none", feature = "inplace_iteration")]
237 unsafe impl<I
: InPlaceIterable
> InPlaceIterable
for Enumerate
<I
> {}