将结构的成员传递给 Rust 中相同结构的方法
Passing a member of a struct to a method of the same struct in Rust
我现在面临Rust中的借用问题,我有一个解决它的想法。但我认为我找到的方式不是一个好的答案。所以我想知道是否有其他方法可以解决。
我用下面的示例代码来描述我的情况:
struct S {
val: u8
}
impl S {
pub fn f1(&mut self) {
println!("F1");
self.f2(self.val);
}
pub fn f2(&mut self, input: u8) {
println!("F2");
// Do something with input
}
}
fn main() {
let mut s = S {
val: 0
};
s.f1();
}
结构 S
有一个方法 f2
,它需要一个额外的参数 input
来做某事。还有一个方法,f1
,用结构体S
的val
调用f2
。对于不同的用例,局外人可以调用 f1
或 f2
。
当我编译上面的代码时,我得到了以下错误信息:
src\main.rs:9:17: 9:25 error: cannot use `self.val` because it was mutably borrowed [E0503]
src\main.rs:9 self.f2(self.val);
^~~~~~~~
src\main.rs:9:9: 9:13 note: borrow of `*self` occurs here
src\main.rs:9 self.f2(self.val);
^~~~
我大致了解了 Rust 中的借用是如何工作的。所以我知道我可以通过将 f1
的实现更改为:
来解决问题
pub fn f1(&mut self) {
let v = self.val;
println!("F1");
self.f2(v);
}
但是,我觉得这个解决方案有点多余。我想知道是否有办法在不使用额外变量绑定的情况下解决这个问题。
您的解决方案有效不是因为额外的变量绑定,而是因为额外的 copy。可以隐式复制整数类型,因此 let v = self.val
创建值的副本。该副本不是从 self
借来的,而是自己拥有的。所以编译器允许你用这个副本调用 f2
。
如果你写self.f2(self.val)
,编译器也会尝试复制self.val
。但是,在这个位置不可能进行复制,因为 self
是为函数调用借用的。所以除非你复制它之前的值,否则不可能进行这样的调用。这不是语法限制,而是借用检查器的强制执行。无论如何,最好按照实际发生的顺序编写复制和调用。
如果您尝试用作参数的类型不是 Copy
(例如 String
),您需要编写 let v = self.val.clone(); self.f2(v);
以明确要求编译器进行复制.不允许在不复制的情况下进行此类调用。您可能需要使方法不可变或以某种方式消除参数。
您可以对可复制值使用此技巧:
pub fn f1(&mut self) {
println!("F1");
match self.val {x => self.f2(x)};
}
但是,使用显式临时变量更加清晰和惯用。
我现在面临Rust中的借用问题,我有一个解决它的想法。但我认为我找到的方式不是一个好的答案。所以我想知道是否有其他方法可以解决。
我用下面的示例代码来描述我的情况:
struct S {
val: u8
}
impl S {
pub fn f1(&mut self) {
println!("F1");
self.f2(self.val);
}
pub fn f2(&mut self, input: u8) {
println!("F2");
// Do something with input
}
}
fn main() {
let mut s = S {
val: 0
};
s.f1();
}
结构 S
有一个方法 f2
,它需要一个额外的参数 input
来做某事。还有一个方法,f1
,用结构体S
的val
调用f2
。对于不同的用例,局外人可以调用 f1
或 f2
。
当我编译上面的代码时,我得到了以下错误信息:
src\main.rs:9:17: 9:25 error: cannot use `self.val` because it was mutably borrowed [E0503]
src\main.rs:9 self.f2(self.val);
^~~~~~~~
src\main.rs:9:9: 9:13 note: borrow of `*self` occurs here
src\main.rs:9 self.f2(self.val);
^~~~
我大致了解了 Rust 中的借用是如何工作的。所以我知道我可以通过将 f1
的实现更改为:
pub fn f1(&mut self) {
let v = self.val;
println!("F1");
self.f2(v);
}
但是,我觉得这个解决方案有点多余。我想知道是否有办法在不使用额外变量绑定的情况下解决这个问题。
您的解决方案有效不是因为额外的变量绑定,而是因为额外的 copy。可以隐式复制整数类型,因此 let v = self.val
创建值的副本。该副本不是从 self
借来的,而是自己拥有的。所以编译器允许你用这个副本调用 f2
。
如果你写self.f2(self.val)
,编译器也会尝试复制self.val
。但是,在这个位置不可能进行复制,因为 self
是为函数调用借用的。所以除非你复制它之前的值,否则不可能进行这样的调用。这不是语法限制,而是借用检查器的强制执行。无论如何,最好按照实际发生的顺序编写复制和调用。
如果您尝试用作参数的类型不是 Copy
(例如 String
),您需要编写 let v = self.val.clone(); self.f2(v);
以明确要求编译器进行复制.不允许在不复制的情况下进行此类调用。您可能需要使方法不可变或以某种方式消除参数。
您可以对可复制值使用此技巧:
pub fn f1(&mut self) {
println!("F1");
match self.val {x => self.f2(x)};
}
但是,使用显式临时变量更加清晰和惯用。