use crate::iter::ParallelIterator; #[derive(Debug)] pub struct Chain { pub(crate) left: T, pub(crate) right: U, pub(crate) left_in_progress: bool, } impl ParallelIterator for Chain where B: Iterator + Send, T: ParallelIterator, U: ParallelIterator, { type Item = T::Item; fn next_batch(&mut self) -> Option { if self.left_in_progress { match self.left.next_batch() { b @ Some(_) => return b, None => self.left_in_progress = false, } } self.right.next_batch() } } #[derive(Debug)] pub struct Map { pub(crate) iter: P, pub(crate) f: F, } impl ParallelIterator> for Map where B: Iterator + Send, U: ParallelIterator, F: FnMut(U::Item) -> T + Send + Clone, { type Item = T; fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.map(self.f.clone())) } } #[derive(Debug)] pub struct Filter { pub(crate) iter: P, pub(crate) predicate: F, } impl ParallelIterator> for Filter where B: Iterator + Send, P: ParallelIterator, F: FnMut(&P::Item) -> bool + Send + Clone, { type Item = P::Item; fn next_batch(&mut self) -> Option> { self.iter .next_batch() .map(|b| b.filter(self.predicate.clone())) } } #[derive(Debug)] pub struct FilterMap { pub(crate) iter: P, pub(crate) f: F, } impl ParallelIterator> for FilterMap where B: Iterator + Send, P: ParallelIterator, F: FnMut(P::Item) -> Option + Send + Clone, { type Item = R; fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.filter_map(self.f.clone())) } } #[derive(Debug)] pub struct FlatMap { pub(crate) iter: P, pub(crate) f: F, } impl ParallelIterator> for FlatMap where B: Iterator + Send, P: ParallelIterator, F: FnMut(P::Item) -> U + Send + Clone, U: IntoIterator, U::IntoIter: Send, { type Item = U::Item; // This extends each batch using the flat map. The other option is // to turn each IntoIter into its own batch. fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.flat_map(self.f.clone())) } } #[derive(Debug)] pub struct Flatten

{ pub(crate) iter: P, } impl ParallelIterator> for Flatten

where B: Iterator + Send, P: ParallelIterator, B::Item: IntoIterator, ::IntoIter: Send, { type Item = ::Item; // This extends each batch using the flatten. The other option is to // turn each IntoIter into its own batch. fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.flatten()) } } #[derive(Debug)] pub struct Fuse

{ pub(crate) iter: Option

, } impl ParallelIterator for Fuse

where B: Iterator + Send, P: ParallelIterator, { type Item = P::Item; fn next_batch(&mut self) -> Option { match &mut self.iter { Some(iter) => match iter.next_batch() { b @ Some(_) => b, None => { self.iter = None; None } }, None => None, } } } #[derive(Debug)] pub struct Inspect { pub(crate) iter: P, pub(crate) f: F, } impl ParallelIterator> for Inspect where B: Iterator + Send, P: ParallelIterator, F: FnMut(&P::Item) + Send + Clone, { type Item = P::Item; fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.inspect(self.f.clone())) } } #[derive(Debug)] pub struct Copied

{ pub(crate) iter: P, } impl<'a, B, P, T> ParallelIterator> for Copied

where B: Iterator + Send, P: ParallelIterator, T: 'a + Copy, { type Item = T; fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.copied()) } } #[derive(Debug)] pub struct Cloned

{ pub(crate) iter: P, } impl<'a, B, P, T> ParallelIterator> for Cloned

where B: Iterator + Send, P: ParallelIterator, T: 'a + Copy, { type Item = T; fn next_batch(&mut self) -> Option> { self.iter.next_batch().map(|b| b.cloned()) } } #[derive(Debug)] pub struct Cycle

{ pub(crate) iter: P, pub(crate) curr: Option

, } impl ParallelIterator for Cycle

where B: Iterator + Send, P: ParallelIterator + Clone, { type Item = P::Item; fn next_batch(&mut self) -> Option { match self.curr.as_mut().and_then(|c| c.next_batch()) { batch @ Some(_) => batch, None => { self.curr = Some(self.iter.clone()); self.next_batch() } } } }