rust新手,看到隐式重借用,有些不解,望能够帮忙解答。
下面代码都是重复可变引用,但为什么通过隐式重借用方式,就可以实现多个可变引用?rust不是明确说同一时间只能有一个可变引用吗?
// err 能够理解,rust明确不能有两个可变引用。
fn compile_err() {
let mut s = String::from("hello");
let r1 = &mut s;
{
let r2 = &mut s;
dbg!(r2);
}
dbg!(r1); // compile ERR
}
// 但通过隐式重借用,为啥就可以,(*r1) 解应用的最终对应的不还是 s?
fn compile_ok() {
let mut s = String::from("hello");
let r1 = &mut s;
{
let r2 = &mut (*r1);
dbg!(r2);
}
dbg!(r1); // compile OK
}
borrow-checker 是一个编译期的检查。在实际的程序中,在编译期看到
*r1
的时候,通常是很难确定其实际对象是什么的。(虽然在你的这个简单的程序中可以比较容易确定,但是这种情况在实际的程序中会是比较少见的。)所以 borrow-check 不会把*r1
跟s
当成同一个对象进行检查。同时,在 r2 存在时,r1 已经不能使用了。因为使用 r1, 通常就意味着要对
*r1
进行 borrow 。borrow-checker 会在 r2 存在时阻止再次对*r1
进行 borrow。比如:
因为,此处的两个对 r1 的使用,分别需要对
*r1
进行 borrow / mutable borrow 。而 r2 的存在使得对*r1
进行此类操作不可能。所以,同时还是只有一个“可用的”对 s 的 mutable borrow。
不会有这个效果。如果
let r1 = &mut s
合法,那么r1
跟r2
将是同时可用的。