Skip to content
This repository was archived by the owner on Apr 28, 2025. It is now read-only.

Commit ae8bf8c

Browse files
committed
Add an iterator that ensures known size
Introduce the `KnownSize` iterator wrapper, which allows providing the size at construction time. This provides an `ExactSizeIterator` implemenation so we can check a generator's value count during testing.
1 parent 0d486fe commit ae8bf8c

File tree

1 file changed

+37
-0
lines changed

1 file changed

+37
-0
lines changed

crates/libm-test/src/gen.rs

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,43 @@ pub mod domain_logspace;
55
pub mod edge_cases;
66
pub mod random;
77

8+
/// A wrapper to turn any iterator into an `ExactSizeIterator`. Asserts the final result to ensure
9+
/// the provided size was correct.
10+
#[derive(Debug)]
11+
pub struct KnownSize<I> {
12+
total: u64,
13+
current: u64,
14+
iter: I,
15+
}
16+
17+
impl<I> KnownSize<I> {
18+
pub fn new(iter: I, total: u64) -> Self {
19+
Self { total, current: 0, iter }
20+
}
21+
}
22+
23+
impl<I: Iterator> Iterator for KnownSize<I> {
24+
type Item = I::Item;
25+
26+
fn next(&mut self) -> Option<Self::Item> {
27+
let next = self.iter.next();
28+
if next.is_some() {
29+
self.current += 1;
30+
return next;
31+
}
32+
33+
assert_eq!(self.current, self.total, "total items did not match expected");
34+
None
35+
}
36+
37+
fn size_hint(&self) -> (usize, Option<usize>) {
38+
let remaining = usize::try_from(self.total - self.current).unwrap();
39+
(remaining, Some(remaining))
40+
}
41+
}
42+
43+
impl<I: Iterator> ExactSizeIterator for KnownSize<I> {}
44+
845
/// Helper type to turn any reusable input into a generator.
946
#[derive(Clone, Debug, Default)]
1047
pub struct CachedInput {

0 commit comments

Comments
 (0)