我目前正在学习Rust,并且正在玩一个简单的计算器。在重构时,我最终得到了一些如下代码:
enum OptionalToken {
Foo,
Bar
}
fn next_token() -> OptionalToken {
// Read input, classify, return
OptionalToken::Foo
}
trait Stack {
// ...
fn dump (mut self);
}
impl Stack for Vec<f64> {
// ...
fn dump (mut self) {
println!("Stack: size={} [", self.len());
for x in self.iter() {
println!(" {}", x);
};
println!("]");
}
}
fn main() {
let mut stack: Vec<f64> = Vec::new();
loop {
let tok = next_token();
match tok {
OptionalToken::Foo => { stack.dump(); }
OptionalToken::Bar => { stack.pop(); }
}
}
}
编译器(每晚构建)失败并出现以下错误(同样的错误实际打印两次,因为我做了两次相同的错误):
src/test.rs:38:37: 38:42 error: use of moved value: `stack`
src/test.rs:38 OptionalToken::Foo => { stack.dump(); }
^~~~~
src/test.rs:38:37: 38:42 note: `stack` moved here because it has type `collections::vec::Vec<f64>`, which is non-copyable
src/test.rs:38 OptionalToken::Foo => { stack.dump(); }
我在这里做错了什么?我需要修改什么才能使这样的代码构造起作用?
答案 0 :(得分:2)
函数签名fn dump(mut self)
(或fn dump(self)
,它没有任何区别,坦率地说,我很惊讶特征中允许mut
意味着该方法采用{{ 1}}按值,即移动它。
没有理由取得所有权。使签名Stack
能够在不移动的情况下调用它。
如果“move”对您来说都是希腊语,请参阅TRPL中的Ownership章节。