Rust
Многопоточность: Arc, Mutex и каналы
Разделяемое состояние между потоками и передача сообщений — оба идиоматичных способа.
Код
use std::sync::atomic::{AtomicUsize, Ordering};
use std::sync::{mpsc, Arc, Mutex};
use std::thread;
fn main() {
// 1. Разделяемое состояние: Arc для владения, Mutex для доступа
let counter = Arc::new(Mutex::new(0));
let handles: Vec<_> = (0..8)
.map(|_| {
let counter = Arc::clone(&counter);
thread::spawn(move || {
for _ in 0..1000 {
*counter.lock().unwrap() += 1;
}
})
})
.collect();
for handle in handles {
handle.join().unwrap();
}
println!("Счётчик: {}", *counter.lock().unwrap()); // 8000
// 2. Атомарный счётчик — быстрее Mutex для простых чисел
let atomic = Arc::new(AtomicUsize::new(0));
thread::scope(|s| {
for _ in 0..4 {
let atomic = Arc::clone(&atomic);
s.spawn(move || { atomic.fetch_add(1, Ordering::Relaxed); });
}
});
println!("Атомарный: {}", atomic.load(Ordering::SeqCst));
// 3. Передача сообщений через канал
let (tx, rx) = mpsc::channel();
for id in 0..3 {
let tx = tx.clone();
thread::spawn(move || tx.send(format!("результат потока {id}")).unwrap());
}
drop(tx); // закрываем последнего отправителя, иначе rx будет ждать вечно
for message in rx {
println!("{message}");
}
}