鉴于
fn greet(peeps: &str) {
println!("Hello, {}", peeps);
}
我能做到:
fn main() {
let a = "World";
thread::spawn(move || greet(a)).join().unwrap();
}
编译器理解线程不会比借用的字符串更长,但这只是&str
的生命周期为'static
的特殊情况。当我尝试使用函数参数执行相同操作时,它不会编译:
fn indirect(peeps: &str) {
thread::spawn(move || greet(&peeps)).join().unwrap();
// Does not compile, for fear that the thread may outlive peeps
}
然而,对于一个人类读者来说,显然情况是线程不能比借来的字符串更长。
我找到了两个解决方法:
制作字符串的副本,可以将其移动到主题中:
fn indirect(peeps: &str) {
let peeps = peeps.to_string();
thread::spawn(move || greet(&peeps)).join().unwrap();
}
或者,使用着名的已弃用的thread::scoped
:
#![feature(scoped)]
fn indirect_scoped(peeps: &str) {
thread::scoped(move || greet(&peeps)).join();
}
我不想为函数参数指定'static
生命周期,我不想做出不必要的复制(解决方法1),我不想使用不推荐使用的功能(解决方法2)。
在这种情况下我该怎么做?
答案 0 :(得分:6)
当您想将借用数据传递给子线程时,使用scoped()
的方法是正确的方法。虽然thread::scoped()
本身由于其不健全而被弃用,但crossbeam或scoped_threadpool之类的替代声音API提供了在稳定的Rust上执行此操作的方法:
extern crate crossbeam;
fn indirect(peeps: &str) {
crossbeam::scope(|scope| {
scope.spawn(|| greet(peeps));
});
}