Skip to content

Commit 6a28459

Browse files
author
Clar Fon
committed
Move ExactSizeIterator to own module
1 parent 34d5624 commit 6a28459

File tree

2 files changed

+145
-143
lines changed

2 files changed

+145
-143
lines changed

src/libcore/iter/traits/exact_size.rs

Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,143 @@
1+
/// An iterator that knows its exact length.
2+
///
3+
/// Many [`Iterator`]s don't know how many times they will iterate, but some do.
4+
/// If an iterator knows how many times it can iterate, providing access to
5+
/// that information can be useful. For example, if you want to iterate
6+
/// backwards, a good start is to know where the end is.
7+
///
8+
/// When implementing an `ExactSizeIterator`, you must also implement
9+
/// [`Iterator`]. When doing so, the implementation of [`size_hint`] *must*
10+
/// return the exact size of the iterator.
11+
///
12+
/// [`Iterator`]: trait.Iterator.html
13+
/// [`size_hint`]: trait.Iterator.html#method.size_hint
14+
///
15+
/// The [`len`] method has a default implementation, so you usually shouldn't
16+
/// implement it. However, you may be able to provide a more performant
17+
/// implementation than the default, so overriding it in this case makes sense.
18+
///
19+
/// [`len`]: #method.len
20+
///
21+
/// # Examples
22+
///
23+
/// Basic usage:
24+
///
25+
/// ```
26+
/// // a finite range knows exactly how many times it will iterate
27+
/// let five = 0..5;
28+
///
29+
/// assert_eq!(5, five.len());
30+
/// ```
31+
///
32+
/// In the [module level docs][moddocs], we implemented an [`Iterator`],
33+
/// `Counter`. Let's implement `ExactSizeIterator` for it as well:
34+
///
35+
/// [moddocs]: index.html
36+
///
37+
/// ```
38+
/// # struct Counter {
39+
/// # count: usize,
40+
/// # }
41+
/// # impl Counter {
42+
/// # fn new() -> Counter {
43+
/// # Counter { count: 0 }
44+
/// # }
45+
/// # }
46+
/// # impl Iterator for Counter {
47+
/// # type Item = usize;
48+
/// # fn next(&mut self) -> Option<usize> {
49+
/// # self.count += 1;
50+
/// # if self.count < 6 {
51+
/// # Some(self.count)
52+
/// # } else {
53+
/// # None
54+
/// # }
55+
/// # }
56+
/// # }
57+
/// impl ExactSizeIterator for Counter {
58+
/// // We can easily calculate the remaining number of iterations.
59+
/// fn len(&self) -> usize {
60+
/// 5 - self.count
61+
/// }
62+
/// }
63+
///
64+
/// // And now we can use it!
65+
///
66+
/// let counter = Counter::new();
67+
///
68+
/// assert_eq!(5, counter.len());
69+
/// ```
70+
#[stable(feature = "rust1", since = "1.0.0")]
71+
pub trait ExactSizeIterator: Iterator {
72+
/// Returns the exact number of times the iterator will iterate.
73+
///
74+
/// This method has a default implementation, so you usually should not
75+
/// implement it directly. However, if you can provide a more efficient
76+
/// implementation, you can do so. See the [trait-level] docs for an
77+
/// example.
78+
///
79+
/// This function has the same safety guarantees as the [`size_hint`]
80+
/// function.
81+
///
82+
/// [trait-level]: trait.ExactSizeIterator.html
83+
/// [`size_hint`]: trait.Iterator.html#method.size_hint
84+
///
85+
/// # Examples
86+
///
87+
/// Basic usage:
88+
///
89+
/// ```
90+
/// // a finite range knows exactly how many times it will iterate
91+
/// let five = 0..5;
92+
///
93+
/// assert_eq!(5, five.len());
94+
/// ```
95+
#[inline]
96+
#[stable(feature = "rust1", since = "1.0.0")]
97+
fn len(&self) -> usize {
98+
let (lower, upper) = self.size_hint();
99+
// Note: This assertion is overly defensive, but it checks the invariant
100+
// guaranteed by the trait. If this trait were rust-internal,
101+
// we could use debug_assert!; assert_eq! will check all Rust user
102+
// implementations too.
103+
assert_eq!(upper, Some(lower));
104+
lower
105+
}
106+
107+
/// Returns whether the iterator is empty.
108+
///
109+
/// This method has a default implementation using `self.len()`, so you
110+
/// don't need to implement it yourself.
111+
///
112+
/// # Examples
113+
///
114+
/// Basic usage:
115+
///
116+
/// ```
117+
/// #![feature(exact_size_is_empty)]
118+
///
119+
/// let mut one_element = std::iter::once(0);
120+
/// assert!(!one_element.is_empty());
121+
///
122+
/// assert_eq!(one_element.next(), Some(0));
123+
/// assert!(one_element.is_empty());
124+
///
125+
/// assert_eq!(one_element.next(), None);
126+
/// ```
127+
#[inline]
128+
#[unstable(feature = "exact_size_is_empty", issue = "35428")]
129+
fn is_empty(&self) -> bool {
130+
self.len() == 0
131+
}
132+
}
133+
134+
#[stable(feature = "rust1", since = "1.0.0")]
135+
impl<I: ExactSizeIterator + ?Sized> ExactSizeIterator for &mut I {
136+
fn len(&self) -> usize {
137+
(**self).len()
138+
}
139+
fn is_empty(&self) -> bool {
140+
(**self).is_empty()
141+
}
142+
}
143+

src/libcore/iter/traits/mod.rs

Lines changed: 2 additions & 143 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@ use num::Wrapping;
33

44
mod iterator;
55
mod double_ended;
6+
mod exact_size;
67

78
pub use self::iterator::Iterator;
89
pub use self::double_ended::DoubleEndedIterator;
10+
pub use self::exact_size::ExactSizeIterator;
911

1012
/// Conversion from an `Iterator`.
1113
///
@@ -357,149 +359,6 @@ impl Extend<()> for () {
357359
}
358360
}
359361

360-
/// An iterator that knows its exact length.
361-
///
362-
/// Many [`Iterator`]s don't know how many times they will iterate, but some do.
363-
/// If an iterator knows how many times it can iterate, providing access to
364-
/// that information can be useful. For example, if you want to iterate
365-
/// backwards, a good start is to know where the end is.
366-
///
367-
/// When implementing an `ExactSizeIterator`, you must also implement
368-
/// [`Iterator`]. When doing so, the implementation of [`size_hint`] *must*
369-
/// return the exact size of the iterator.
370-
///
371-
/// [`Iterator`]: trait.Iterator.html
372-
/// [`size_hint`]: trait.Iterator.html#method.size_hint
373-
///
374-
/// The [`len`] method has a default implementation, so you usually shouldn't
375-
/// implement it. However, you may be able to provide a more performant
376-
/// implementation than the default, so overriding it in this case makes sense.
377-
///
378-
/// [`len`]: #method.len
379-
///
380-
/// # Examples
381-
///
382-
/// Basic usage:
383-
///
384-
/// ```
385-
/// // a finite range knows exactly how many times it will iterate
386-
/// let five = 0..5;
387-
///
388-
/// assert_eq!(5, five.len());
389-
/// ```
390-
///
391-
/// In the [module level docs][moddocs], we implemented an [`Iterator`],
392-
/// `Counter`. Let's implement `ExactSizeIterator` for it as well:
393-
///
394-
/// [moddocs]: index.html
395-
///
396-
/// ```
397-
/// # struct Counter {
398-
/// # count: usize,
399-
/// # }
400-
/// # impl Counter {
401-
/// # fn new() -> Counter {
402-
/// # Counter { count: 0 }
403-
/// # }
404-
/// # }
405-
/// # impl Iterator for Counter {
406-
/// # type Item = usize;
407-
/// # fn next(&mut self) -> Option<usize> {
408-
/// # self.count += 1;
409-
/// # if self.count < 6 {
410-
/// # Some(self.count)
411-
/// # } else {
412-
/// # None
413-
/// # }
414-
/// # }
415-
/// # }
416-
/// impl ExactSizeIterator for Counter {
417-
/// // We can easily calculate the remaining number of iterations.
418-
/// fn len(&self) -> usize {
419-
/// 5 - self.count
420-
/// }
421-
/// }
422-
///
423-
/// // And now we can use it!
424-
///
425-
/// let counter = Counter::new();
426-
///
427-
/// assert_eq!(5, counter.len());
428-
/// ```
429-
#[stable(feature = "rust1", since = "1.0.0")]
430-
pub trait ExactSizeIterator: Iterator {
431-
/// Returns the exact number of times the iterator will iterate.
432-
///
433-
/// This method has a default implementation, so you usually should not
434-
/// implement it directly. However, if you can provide a more efficient
435-
/// implementation, you can do so. See the [trait-level] docs for an
436-
/// example.
437-
///
438-
/// This function has the same safety guarantees as the [`size_hint`]
439-
/// function.
440-
///
441-
/// [trait-level]: trait.ExactSizeIterator.html
442-
/// [`size_hint`]: trait.Iterator.html#method.size_hint
443-
///
444-
/// # Examples
445-
///
446-
/// Basic usage:
447-
///
448-
/// ```
449-
/// // a finite range knows exactly how many times it will iterate
450-
/// let five = 0..5;
451-
///
452-
/// assert_eq!(5, five.len());
453-
/// ```
454-
#[inline]
455-
#[stable(feature = "rust1", since = "1.0.0")]
456-
fn len(&self) -> usize {
457-
let (lower, upper) = self.size_hint();
458-
// Note: This assertion is overly defensive, but it checks the invariant
459-
// guaranteed by the trait. If this trait were rust-internal,
460-
// we could use debug_assert!; assert_eq! will check all Rust user
461-
// implementations too.
462-
assert_eq!(upper, Some(lower));
463-
lower
464-
}
465-
466-
/// Returns whether the iterator is empty.
467-
///
468-
/// This method has a default implementation using `self.len()`, so you
469-
/// don't need to implement it yourself.
470-
///
471-
/// # Examples
472-
///
473-
/// Basic usage:
474-
///
475-
/// ```
476-
/// #![feature(exact_size_is_empty)]
477-
///
478-
/// let mut one_element = std::iter::once(0);
479-
/// assert!(!one_element.is_empty());
480-
///
481-
/// assert_eq!(one_element.next(), Some(0));
482-
/// assert!(one_element.is_empty());
483-
///
484-
/// assert_eq!(one_element.next(), None);
485-
/// ```
486-
#[inline]
487-
#[unstable(feature = "exact_size_is_empty", issue = "35428")]
488-
fn is_empty(&self) -> bool {
489-
self.len() == 0
490-
}
491-
}
492-
493-
#[stable(feature = "rust1", since = "1.0.0")]
494-
impl<I: ExactSizeIterator + ?Sized> ExactSizeIterator for &mut I {
495-
fn len(&self) -> usize {
496-
(**self).len()
497-
}
498-
fn is_empty(&self) -> bool {
499-
(**self).is_empty()
500-
}
501-
}
502-
503362
/// Trait to represent types that can be created by summing up an iterator.
504363
///
505364
/// This trait is used to implement the [`sum`] method on iterators. Types which

0 commit comments

Comments
 (0)