为什么借用顺序在 Rust 中很重要?

Raf*_*ael 7 rust

fn say_hello(s: &str) {
    println!("Hello {}", s);
}
Run Code Online (Sandbox Code Playgroud)

为什么这样做

fn main() {
    let mut name = String::from("Charlie");
    let x = &mut name;
    say_hello(x);
    name.push_str(" Brown");
}
Run Code Online (Sandbox Code Playgroud)

但这不是吗?

fn main() {
    let mut name = String::from("Charlie");
    let x = &mut name;
    name.push_str(" Brown");
    say_hello(x);
}
Run Code Online (Sandbox Code Playgroud)

我所做的只是切换两个函数的顺序,但似乎x在这两种情况下都可变地借用了 name,而 push_str 也可变地借用了 name,那么为什么第一个示例编译?

如果我取消调用,say_hello()即使仍然有两个可变借用,为什么两者的顺序无关紧要?

编辑:这相似吗?

fn change_string(s: &mut String) { // s is mutably borrowed but isn't used yet
    println!("{}", s.is_empty()); // so the scopes don't overlap even though is_empty is making an immutable borrow?
    s.push_str(" Brown");
}
Run Code Online (Sandbox Code Playgroud)

kmd*_*eko 10

Rust 的借用规则之一是可变引用是独占的。意思是,虽然x活着,name但不能使用。

那么,为什么第一个示例即使x仍在范围内也能编译?因为 Rust 也有非词法生命周期,意思是x在最后一次使用后停止“存活”。

fn main() {
    let mut name = String::from("Charlie");
    let x = &mut name;
    say_hello(x);            // "x"s lifetime ends here, releasing the exclusive borrow
    name.push_str(" Brown"); // "name" can be used again
}
Run Code Online (Sandbox Code Playgroud)


Psi*_*dom 5

因为在您的第一种情况下,两个可变借用范围不重叠,并且在任何给定时间点只有一个借用;但在您的第二种情况下,它们重叠,这意味着您在某个时间点有多个可变借用,这是不允许的:

第一种情况:

fn main() {
    let mut name = String::from("Charlie");
    let x = &mut name;
    say_hello(x);             // the mutable borrow ends here
    name.push_str(" Brown");  // a new mutable borrow
}
Run Code Online (Sandbox Code Playgroud)

第二种情况:

fn main() {
    let mut name = String::from("Charlie");
    let x = &mut name;
    name.push_str(" Brown");  // the first mutable borrow is still 
                      // alive, you have two mutable borrows here
    say_hello(x);       // the first mutable borrow ends here
}
Run Code Online (Sandbox Code Playgroud)