Un pool de workers en Rust
Trabajos por un canal, resultados de vuelta por otro — un pool en veinte líneas.
use std::sync::{mpsc, Arc, Mutex};
use std::thread;
fn main() {
let (jobs_tx, jobs_rx) = mpsc::channel::<u64>();
let (out_tx, out_rx) = mpsc::channel::<(u64, u64)>();
let jobs_rx = Arc::new(Mutex::new(jobs_rx));
for _ in 0..3 {
let jobs_rx = Arc::clone(&jobs_rx);
let out_tx = out_tx.clone();
thread::spawn(move || loop {
let job = match jobs_rx.lock().unwrap().recv() {
Ok(job) => job,
Err(_) => break,
};
let squared = job * job;
out_tx.send((job, squared)).unwrap();
});
}
drop(out_tx);
for n in 1..=6 {
jobs_tx.send(n).unwrap();
}
drop(jobs_tx);
let mut results: Vec<(u64, u64)> = out_rx.iter().collect();
results.sort();
println!("{:?}", results);
}
Cómo funciona
- El canal de trabajos se comparte tras un
Arc<Mutex<Receiver>>. - Cada worker itera hasta que el canal de trabajos se cierra.
- Los resultados llegan en orden de término, no de envío.
Palabras clave y builtins usados aquí
ErrOkVecbreakdropfnforinletloopmatchmovemutu64use
El intento, en números
- Líneas
- 31
- Caracteres a escribir
- 658
- Tokens
- 245
- Ritmo de tres estrellas
- 105 tpm
Al ritmo de tres estrellas de 105 tokens por minuto, este intento toma unos 140 segundos.
Paso 2 de 2 en Canales; paso 8 de 15 en Concurrencia y async.