面试题答案
一键面试-
使用的机制:
Arc
(原子引用计数):用于在多个线程间共享数据。Arc
允许在堆上分配的数据有多个所有者,同时提供原子引用计数,使得在多线程环境下安全地共享数据成为可能。Mutex
(互斥锁):用于保护共享数据,确保同一时间只有一个线程可以访问数据。当一个线程获取了Mutex
的锁,其他线程必须等待锁被释放才能访问被保护的数据。async_std::sync::Arc
和async_std::sync::Mutex
:在异步编程场景下,async_std
库提供了异步版本的Arc
和Mutex
,用于在异步任务间安全地共享状态。
-
代码示例:
use std::sync::{Arc, Mutex};
use std::thread;
// 普通线程场景
fn main() {
let counter = Arc::new(Mutex::new(0));
let mut handles = vec![];
for _ in 0..10 {
let counter = Arc::clone(&counter);
let handle = thread::spawn(move || {
let mut num = counter.lock().unwrap();
*num += 1;
});
handles.push(handle);
}
for handle in handles {
handle.join().unwrap();
}
println!("Final counter value: {}", *counter.lock().unwrap());
}
// 异步场景
use async_std::prelude::*;
use async_std::sync::{Arc, Mutex};
use async_std::task;
#[async_std::main]
async fn main() {
let counter = Arc::new(Mutex::new(0));
let mut tasks = vec![];
for _ in 0..10 {
let counter = Arc::clone(&counter);
let task = task::spawn(async move {
let mut num = counter.lock().await;
*num += 1;
});
tasks.push(task);
}
for task in tasks {
task.await.unwrap();
}
println!("Final counter value: {}", *counter.lock().await);
}
在上述代码中:
- 普通线程场景使用了
std::sync::Arc
和std::sync::Mutex
,通过thread::spawn
创建线程,在线程中获取Mutex
的锁来修改共享的计数器。 - 异步场景使用了
async_std::sync::Arc
和async_std::sync::Mutex
,通过async_std::task::spawn
创建异步任务,在异步任务中通过await
获取Mutex
的锁来修改共享的计数器。