我正在尝试在可以通过引用进行变异的特征中获得一个值。问题是 String
值非常大并且可能被许多线程访问,所以我的解决方案看起来像这样:
trait MyTrait {
fn name<'a>(&'a mut self) -> &'a mut String;
}
struct SimpleImpl {
name: String
}
impl MyTrait for SimpleImpl {
fn name<'a>(&'a mut self) -> &'a mut String {
&mut self.name
}
}
use std::sync::{Arc,RwLock};
struct ParallelImpl {
name: Arc<RwLock<String>>
}
impl MyTrait for ParallelImpl {
fn name<'a>(&'a mut self) -> &'a mut String {
self.name.get_mut().unwrap()
}
}
fn main() {
let mut a = SimpleImpl { name: String::from("simple") };
let mut b = ParallelImpl { name: Arc::new(RwLock::new(String::from("parallel"))) };
a.name().as_mut_str();
b.name().as_mut_str();
}
编译失败
main2.rs:23:9: 23:18 error: cannot borrow immutable borrowed content as mutable
main2.rs:23 self.name.get_mut().unwrap()
为什么我不能调用 get_mut()
来解包 Arc
和 RwLock
?
最佳答案
再看一下RwLock
的界面.
get_mut
返回 LockResult<&mut T>
这是一个守卫对象。破坏这个守卫会自动打开锁。
为了安全起见,&mut T
您可以通过调用 unwrap()
获得on the guard 是从guard借用,即unwrap()
的结果的生命周期受守卫的限制(因为守卫被摧毁后,锁被解锁)。
而在这里,你正在创建一个临时守卫并立即将其丢弃,因此引用的生命周期不能超过函数的生命周期...
恭喜 Rust! 在编译时阻止了另一场数据竞争 :)
关于rust - 将 Arc<RwLock> 转换为 &mut,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40915716/