ParallelExtend

Trait ParallelExtend 

Source
pub trait ParallelExtend<'a, I, T>: Send + Sized
where I: Send + 'a, T: Send, <Self::Consumer as Consumer<I>>::Reducer: Reducer<T>,
{ type Consumer: Consumer<I, Result = T> + 'a; // Required methods fn into_consumer(self) -> Self::Consumer; fn map_result(inner: <Self::Consumer as Consumer<I>>::Result) -> Self; // Provided method fn par_extend<X>( self, iter: X, ) -> ParallelExtendDriver<'a, X::Iter, Self, T> where X: IntoParallelIterator<'a, Item = I> { ... } }
Expand description

ParallelExtend extends an existing collection with items from a ParallelIterator.

§Examples

Implementing ParallelExtend for your type:

use asparit::*;
use std::mem;

struct BlackHole {
    mass: usize,
}

impl<'a, I> ParallelExtend<'a, I, BlackHoleFolder<'a>> for &'a mut BlackHole
where
    I: Send + 'a,
{
    type Consumer = BlackHoleConsumer<'a>;

    fn into_consumer(self) -> Self::Consumer {
        BlackHoleConsumer(Some(self))
    }

    fn map_result(ret: BlackHoleFolder<'a>) -> Self {
        let bh = ret.bh.unwrap();

        bh.mass += ret.mass;

        bh
    }
}

struct BlackHoleConsumer<'a>(Option<&'a mut BlackHole>);

impl WithSetup for BlackHoleConsumer<'_> {}

impl<'a, I> Consumer<I> for BlackHoleConsumer<'a> {
    type Folder = BlackHoleFolder<'a>;
    type Reducer = BlackHoleReducer;
    type Result = BlackHoleFolder<'a>;

    fn split(self) -> (Self, Self, Self::Reducer) {
        (
            BlackHoleConsumer(self.0),
            BlackHoleConsumer(None),
            BlackHoleReducer,
        )
    }

    fn split_at(self, _index: usize) -> (Self, Self, Self::Reducer) {
        (
            BlackHoleConsumer(self.0),
            BlackHoleConsumer(None),
            BlackHoleReducer,
        )
    }

    fn into_folder(self) -> Self::Folder {
        BlackHoleFolder {
            bh: self.0,
            mass: 0,
        }
    }
}

struct BlackHoleFolder<'a> {
    bh: Option<&'a mut BlackHole>,
    mass: usize,
}

impl<'a, I> Folder<I> for BlackHoleFolder<'a> {
    type Result = Self;

    fn consume(mut self, _item: I) -> Self {
        self.mass += std::mem::size_of::<I>();

        self
    }

    fn consume_iter<X>(mut self, iter: X) -> Self
    where
        X: IntoIterator<Item = I>,
    {
        self.mass += iter.into_iter().count() * std::mem::size_of::<I>();

        self
    }

    fn complete(self) -> Self::Result {
        self
    }
}

struct BlackHoleReducer;

impl<'a> Reducer<BlackHoleFolder<'a>> for BlackHoleReducer {
    fn reduce(
        self,
        left: BlackHoleFolder<'a>,
        right: BlackHoleFolder<'a>,
    ) -> BlackHoleFolder<'a> {
        BlackHoleFolder {
            bh: left.bh.or(right.bh),
            mass: left.mass + right.mass,
        }
    }
}

let mut bh = BlackHole { mass: 0 };

bh.par_extend(0i32..1000).exec();
assert_eq!(bh.mass, 4000);

bh.par_extend(0i64..10).exec();
assert_eq!(bh.mass, 4080);

Required Associated Types§

Source

type Consumer: Consumer<I, Result = T> + 'a

Required Methods§

Source

fn into_consumer(self) -> Self::Consumer

Creates a consumer that is used to handle the items from the iterator.

Source

fn map_result(inner: <Self::Consumer as Consumer<I>>::Result) -> Self

Converts the result of the consumer into the final type

Provided Methods§

Source

fn par_extend<X>(self, iter: X) -> ParallelExtendDriver<'a, X::Iter, Self, T>
where X: IntoParallelIterator<'a, Item = I>,

Dyn Compatibility§

This trait is not dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety", so this trait is not object safe.

Implementors§