我写了一些Rust代码&String作为参数:
fn awesome_greeting(name: &String) {
println!("Wow, you are awesome, {}!", name);
}
Run Code Online (Sandbox Code Playgroud)
我还编写了代码来引用a Vec或Box:
fn total_price(prices: &Vec<i32>) -> i32 {
prices.iter().sum()
}
fn is_even(value: &Box<i32>) -> bool {
**value % 2 == 0
}
Run Code Online (Sandbox Code Playgroud)
但是,我收到一些反馈意见,这样做并不是一个好主意.为什么不?
从std::cell文档中,我看到Cell"只与实现的类型兼容Copy".这意味着我必须使用RefCell非Copy类型.
当我这样做有一个Copy类型,是否有使用一种类型的细胞在另一个好处?我假设答案是肯定的,因为否则两种类型都不存在!使用一种类型而不是另一种类型有什么好处和权衡?
这是一个愚蠢的,虚构的例子,使用两者Cell并RefCell实现相同的目标:
use std::cell::{Cell,RefCell};
struct ThingWithCell {
counter: Cell<u8>,
}
impl ThingWithCell {
fn new() -> ThingWithCell {
ThingWithCell { counter: Cell::new(0) }
}
fn increment(&self) {
self.counter.set(self.counter.get() + 1);
}
fn count(&self) -> u8 { self.counter.get() }
}
struct ThingWithRefCell {
counter: RefCell<u8>,
}
impl ThingWithRefCell {
fn new() -> ThingWithRefCell {
ThingWithRefCell { counter: RefCell::new(0) }
}
fn …Run Code Online (Sandbox Code Playgroud) 您什么时候需要使用Cell或RefCell?似乎有许多其他类型选择适合代替这些,文档警告说使用RefCell是一种"最后的手段".
使用这些类型是" 代码味 "吗?任何人都可以展示一个例子,使用这些类型比使用其他类型更有意义,例如Rc甚至Box?
我想创建一个Rc<str>因为我想减少间接跟随访问Rc<String>需求的2个指针.我需要使用一个,Rc因为我真的拥有共享权.我详细介绍了我在字符串类型中遇到的更具体问题.
Rc 有一个?Sized约束:
pub struct Rc<T: ?Sized> { /* fields omitted */ }
Run Code Online (Sandbox Code Playgroud)
我还听说Rust 1.2将提供适当的支持来存储未经过类型化的类型Rc,但我不确定它与1.1的区别.
以str案例为例,我的天真尝试(也就是从a构建String)也失败了:
use std::rc::Rc;
fn main() {
let a: &str = "test";
let b: Rc<str> = Rc::new(*a);
println!("{}", b);
}
Run Code Online (Sandbox Code Playgroud)
error[E0277]: the trait bound `str: std::marker::Sized` is not satisfied
--> src/main.rs:5:22
|
5 | let b: Rc<str> = Rc::new(*a);
| ^^^^^^^ `str` does not have …Run Code Online (Sandbox Code Playgroud) 锈智能指针之间存在类比std::rc::Rc,并std::sync::Arc与C ++智能指针std::shared_ptr和std::atomic_shared_ptr?对我来说,它们看起来一样,但可能有一些实现上的细微差别。例如在 C++std::shared_ptr中,控制块中的引用计数是原子的,尽管指针本身不是。在 Rust 中是一样的std::rc::Rc吗?