编者注:这个问题在Rust 1.0之前被问过,并且从那时起一些语法发生了变化,但基本概念仍然存在。一些答案已针对Rust 1.0语法进行了更新。
我是Rust的新手并尝试使用JavaScript,Python等无关紧要的闭包做一些事情,但我遇到Rust的终身问题。我理解错误信息,但它让我相信我想要做的事情在Rust中很难。
我只想创建一个函数数组a
,这样
a[0]
是返回0的函数a[1]
是返回1 a[9]
是返回9 我试过了:
fn main() {
let a : [||->uint, ..10];
for i in range(0u, 10) {
a[i] = ||{i};
}
println!("{} {} {}", a[1](), a[5](), a[9]())
}
但我有一生的错误。由于需求冲突,报告的错误是“#34;无法推断出合适的生命周期”。对于a
中的函数,因为生命周期不能超过while
块,因此闭包不会比它们的堆栈帧寿命更长,这当然是因为我在println!
中调用它们。
我确定必须有办法建立这个函数数组,但是如何?
答案 0 :(得分:5)
您需要使用move || i
。
move
表示此闭包将按值而不是引用取i
。默认情况下,这些闭包只会引用i
。在你的情况下,它是被禁止的,因为i
的生命周期仅限于循环体。
另外,Rust会抱怨你的阵列可能没有完全初始化。为避免这种情况,您可以使用Vec<_>
,也可以使用std::mem::uninitialized
:
fn main() {
let mut a: [_; 10] = unsafe { std::mem::uninitialized() };
for i in 0..10 {
a[i] = move || i;
}
println!("{} {} {}", a[1](), a[5](), a[9]())
}
答案 1 :(得分:4)
可以collect
从迭代器到Vec
的多个闭包:
fn main() {
let a: Vec<_> = (0..10).map(|i| move || i).collect();
println!("{} {} {}", a[1](), a[5](), a[9]());
}
move
关键字会导致i
的所有权转移到关闭。
另见: