Rust智能指针
# 智能指针
# Mutex
#![feature(mutex_unlock)]
use std::sync::{RwLock, Mutex};
fn main(){
let p = Mutex::new(0);
let mut guard = p.lock().unwrap();
*guard += 20;
Mutex::unlock(guard);
}
1
2
3
4
5
6
7
8
2
3
4
5
6
7
8
# RwLock
读写锁分开,离开作用域就结束
use std::sync::RwLock;
let lock = RwLock::new(5);
// 可以一次持有许多 reader 锁
{
let r1 = lock.read().unwrap();
let r2 = lock.read().unwrap();
assert_eq!(*r1, 5);
assert_eq!(*r2, 5);
} // 此时将丢弃读锁
// 只能持有一个写锁,但是
{
let mut w = lock.write().unwrap();
*w += 1;
assert_eq!(*w, 6);
} // 写锁在这里被丢弃
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# Box
很简单就是将数据存储到栈中,可以解引用拿到数据
fn main(){
let mut e = Box::new(0);
*e=3;
println!("{}",e);
}
1
2
3
4
5
2
3
4
5
# Arc
线程安全的Rc
fn main(){
let e = Arc::new(Cell::new(0));
let w = e.clone();
(*e).set(320);
println!("{}",(*e).get());
assert!((*e).get()==320);
(*w).set(60);
println!("{}",(*e).get());
assert!((*e).get()==60);
}
1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
# Rc
提供多所有权,多个身份可以共同拥有此数据,拥有了这个cell
fn main(){
let e = Rc::new(Cell::new(0));
let w = e.clone();
(*e).set(320);
println!("{}",(*e).get());
assert!((*e).get()==320);
(*w).set(60);
println!("{}",(*e).get());
assert!((*e).get()==60);
}
1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
# Cell
实现替换值的内部可变性,传入的数据必须实现Copy tirte,修改是直接替换
let p =Cell::new(0);
p.set(3);
let s = p.get();
assert!(s==3);
1
2
3
4
2
3
4
# RefCell
实现可变引用方式的内部可变性,修改是自己判断
fn main(){
let p = RefCell::new(0);
*(p.borrow_mut())=1;
println!("{}",*(p.borrow()));
}
1
2
3
4
5
2
3
4
5
# Weak
防止循环引用
# UnsafeCell
use std::{cell::{RefCell}, sync::{Arc, Mutex}, panic::Location};
fn test(t:&Arc<Mutex<Vec<String>>>)->Result<(),Box<dyn std::error::Error>>{
let s=Arc::clone(t);
let lock;
if let Ok(g)= s.lock() {
lock =g;
let c= lock.clone();
let mut res = vec![];
for i in c.iter(){
res.push(i.clone());
}
return Ok(());
};
Ok(())
}
fn main(){
let s= {
let u = Arc::new(vec!["ss".to_string()]);
let _s = (&u).clone();
// 这里会报错因为可变性没有变化
// u.push("ssssww".to_string());
// 这里可以获取Vec的可变引用
let u = Arc::new(RefCell::new(vec!["aa".to_string()]));
let s = (&u).clone();
u.borrow_mut().push("22222".to_string());
s
// 这里可以使用Cell进行替代,但是使用起来很麻烦而且开销要大,因为是直接的复制,还要这里的Vec实现CopyTrit
// let e=Arc::new(Cell::new(Vec::<String>::new()));
// let tmp =(*e).get()
};
println!("{:?}",(*s).borrow());
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
编辑 (opens new window)
上次更新: 2024/04/16, 00:35:21