dynpool

Crates.iodynpool
lib.rsdynpool
version0.0.2
sourcesrc
created_at2018-10-23 06:56:33.880162
updated_at2019-09-04 02:30:26.043618
descriptionA thread manager that is lightweight, flexible, and rescalable.
homepage
repositoryhttps://gitlab.com/samsartor/dynpool
max_upload_size
id92125
size68,269
Sam Sartor (samsartor)

documentation

https://docs.rs/dynpool/

README

Build Status

Dynpool

Dynpool is a thread manager that is lightweight, flexible, and rescalable. The pool is designed for minimal overhead, without expensive locks or an extra management thread. Add a job queue yourself, or don't!

To use dynpool, all you need is an implementation of System. The pool will repeatedly call System::work from many threads, each with a per-thread data object. Rather than requiring you to rescale the pool from the outside, dynpool will constantly query the worker count from System::scale. This is actually faster, since a simple scale implementation can be inlined into the worker! Your system can be run in the background, and controlled through the Pool object, or run in the foreground to make use of the current thread.

struct Printer(Instant);

impl System for Printer {
    type Data = String;

    // How many threads? The pool will scale up over time!
    fn scale(&self) -> Scale {
        let time = self.0.elapsed();
        let ms = time.as_secs() * 1000 + time.subsec_millis() as u64;
        match ms {
            0..=200 => Scale::active(1),
            201..=400 => Scale::active(2),
            401..=600 => Scale::active(3),
            601..=800 => Scale::active(4),
            _ => Scale::shutdown(),
        }
    }

    // Pick a string for each thread.
    fn init(&self, index: usize) -> String {
        match index {
            0 => "Hello",
            1 => "Hola",
            2 => "Bonjour",
            3 => "Ciao",
            _ => unreachable!(),
        }.to_owned()
    }

    // Do work on several threads!
    fn work(&self, text: &mut String) -> Decision {
        println!("{}", text);
        *text += " Again";
        sleep(Duration::from_millis(100));
        Decision::Again
    }
}

fn main() {
    Pool::start_fg(Printer(Instant::now())).unwrap();
    println!("This is the end!");
}

There are also builtin functions for concisely altering and constructing systems.

let workers = func_worker(|index| {
    println!("New worker #{}", index);
    move || {
        println!("Hello from #{}", index);
        Decision::Again
    }
});
let sys = with_threads(workers, 10);
let end_time = Instant::now() + Duration::from_millis(500);
Pool::start_fg(shutdown_after(sys, end_time)).unwrap();
Commit count: 25

cargo fmt