pub struct PeekingIter<I> {
iter: I,
peeking: Option<I>,
}
pub trait Peeking: Iterator {
fn peek(&mut self) -> Option<Self::Item>;
fn advance_to_peeked(&mut self);
fn rewind_peeking(&mut self);
fn peek_nth(&mut self, n: usize) -> Option<Self::Item> {
for _ in 0..n {
self.peek();
}
self.peek()
}
fn next_while<F: Fn(&Self::Item) -> bool>(&mut self, pred: F) -> Vec<Self::Item> {
let mut result = vec![];
self.rewind_peeking();
loop {
match self.peek() {
None => break,
Some(x) => {
if pred(&x) {
result.push(x);
self.next();
} else {
break;
}
}
}
}
self.rewind_peeking();
result
}
fn next_while1<F: Fn(&Self::Item) -> bool>(&mut self, pred: F) -> Vec<Self::Item> {
let mut result = vec![];
loop {
match self.next() {
None => break,
Some(x) => {
if pred(&x) {
result.push(x)
} else {
break;
}
}
}
}
result
}
}
pub trait ToPeeking
where
Self: Sized,
{
fn to_peeking(self) -> PeekingIter<Self>;
}
impl<I: Iterator> PeekingIter<I> {
pub fn new(iter: I) -> Self {
Self {
iter,
peeking: None,
}
}
pub fn next(&mut self) -> Option<I::Item> {
self.peeking = None;
self.iter.next()
}
pub fn into_inner(value: Self) -> I {
value.iter
}
}
impl<I: Iterator + Clone> Peeking for PeekingIter<I> {
fn peek(&mut self) -> Option<Self::Item> {
self.peeking.get_or_insert_with(|| self.iter.clone()).next()
}
fn advance_to_peeked(&mut self) {
if let Some(ref peeking) = self.peeking {
self.iter = peeking.clone();
}
}
fn rewind_peeking(&mut self) {
self.peeking = None;
}
fn peek_nth(&mut self, n: usize) -> Option<I::Item> {
self.peeking
.get_or_insert_with(|| self.iter.clone())
.skip(n)
.next()
}
}
impl<I: Iterator + Clone> Iterator for PeekingIter<I> {
type Item = I::Item;
fn next(&mut self) -> Option<Self::Item> {
PeekingIter::next(self)
}
}
impl<I: Iterator + Clone> ToPeeking for I {
fn to_peeking(self) -> PeekingIter<Self> {
PeekingIter::new(self)
}
}