use super::CollectorBase;
use std::ops::ControlFlow;
pub trait Collector<T>: CollectorBase {
fn collect(&mut self, item: T) -> ControlFlow<()>;
fn collect_many(&mut self, items: impl IntoIterator<Item = T>) -> ControlFlow<()>
where
Self: Sized,
{
self.break_hint()?;
items.into_iter().try_for_each(|item| self.collect(item))
}
fn collect_then_finish(self, items: impl IntoIterator<Item = T>) -> Self::Output
where
Self: Sized,
{
let mut this = self;
let _ = this.collect_many(items);
this.finish()
}
}
impl<C, T> Collector<T> for &mut C
where
C: Collector<T>,
{
#[inline]
fn collect(&mut self, item: T) -> ControlFlow<()> {
C::collect(self, item)
}
#[inline]
fn collect_many(&mut self, items: impl IntoIterator<Item = T>) -> ControlFlow<()> {
C::collect_many(self, items)
}
}
macro_rules! dyn_impl {
($($traits:ident)*) => {
impl<'a, T> Collector<T> for &mut (dyn Collector<T> $(+ $traits)* + 'a) {
#[inline]
fn collect(&mut self, item: T) -> ControlFlow<()> {
<dyn Collector<T>>::collect(*self, item)
}
}
};
}
dyn_impl!();
dyn_impl!(Send);
dyn_impl!(Sync);
dyn_impl!(Send Sync);
fn _dyn_compatible<T>(_: &mut dyn Collector<T>) {}