rust 小白,求教所有权报错

2021-09-09 14:26:41 +08:00
 echotpq

rust 小白,求教

1 、合法不会报错 fn main() {

let mut s = String::from("hello");

let r1 = &mut s;

let r2 = r1;

println!("{}",r2);

println!("{}",s);

}

2 、报错,提示 mutable & immutable 错误

fn main() {

let mut s = String::from("hello");

let r1 = &mut s;

let r2 = r1;

println!("{}",s);

println!("{}",r2);

}

两者有什么区别,请高手指教一下

1070 次点击
所在节点    问与答
5 条回复
misdake
2021-09-09 14:57:29 +08:00
1 里面,r2 在 println 之后就还回去了,所以 s 可以接着用
2 里面,打印 s 的时候,r2 还借着 s 的 mut 引用,所以不能访问 s
echotpq
2021-09-09 15:23:14 +08:00
可是 1 里面 r2 在 println 一次之后,还能继续 println 一次 ,比如 println!("{}",r2); println!("{}",r2); println!("{}",s);
不是 println 一次之后就还回去了吗?怎么还能继续 println 呢?@misdake
XiaoxiaoPu
2021-09-09 15:43:47 +08:00
kaisery.github.io/trpl-zh-cn/ch04-02-references-and-borrowing.html
注意一个引用的作用域从声明的地方开始一直持续到最后一次使用为止。

1 里面,r2 的最后一次使用在第 5 行,后面就不在 r2 的作用域了
2 里面,r2 的最后一次使用在第 6 行,第 5 行的时候 r2 还是有效的
echotpq
2021-09-09 15:51:38 +08:00
@XiaoxiaoPu 谢谢,明白了
ke1e
2021-09-09 17:10:05 +08:00
个人理解:

首先,引用是否有效,取决于它引用的对象是否有效;

在 1 中:r2 是 s 的可变引用,s 在 println!("{}",s); 后被清除失效,所以'a (从 s 被定义到 println 之间)都是存活有效的,rust 的引用检查器自然会认为在'a 中,r2 的引用是有效的。这样你在'a 中调用 println!("{}",r2);都是合法的;

在 2 中:同样道理,println!("{}",r2); 在 'a 之外被调用,此时 s 已经被清除,它的引用也都是失效的,所以不合法

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/800821

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX