4 个版本 (2 个破坏性更新)
0.2.1 | 2022年1月28日 |
---|---|
0.2.0 | 2022年1月19日 |
0.1.0 | 2021年4月11日 |
0.0.1 | 2021年3月26日 |
#684 in 内存管理
每月 25 次下载
37KB
855 行
Bronze
安装
要使用 Bronze,您必须使用 nightly Rust 工具。要安装它们,请在命令行上运行 rustup default nightly
。
使用方法
有时,Rust 中所有变量都有一个所有者的要求可能难以解决。例如,在 Rust 中实现双向链表非常困难,因为每个节点必须被引用两次。此外,特别是对于正在学习 Rust 的人来说,暂时避免“每个变量都有一个所有者”的限制可能更容易。
Bronze 通过引入一个新的智能指针类型 GcRef 来放宽 Rust 的一些限制,该类型描述了对垃圾回收堆位置的指针。在使用 Bronze 时,位于 栈 上的数据具有所有常规 Rust 所有者要求。然而,Bronze 允许将数据移动到 堆。如果类型 T
的值位于堆上,Bronze 允许多个 GcRef<T>
引用对该值。
例如,没有 Bronze,我们必须仔细管理引用和生存期
pub struct IntContainer {
n: i32,
}
pub fn set(c: &mut IntContainer, n: i32) {
c.n = n;
}
pub fn test() {
let c1 = IntContainer{n: 42};
let mut c2 = c1;
// Can't use c1 anymore because it's been moved to c2
set(&mut c2, 42);
}
使用 Bronze,可以通过智能指针引用不是 Copy
的类型,这些智能指针是 Copy
。可以通过 borrow()
和 borrow_mut
获取临时不可变和不可变借用;这些实现 Deref
,允许方便地访问。
//
#[derive(Trace, Finalize)]
pub struct IntContainer {
n: i32,
}
pub fn set(mut c: GcRef<IntContainer>, n: i32) {
c.borrow_mut().n = n;
}
pub fn test() {
let c1 = GcRef::new(IntContainer{n: 42});
let c2 = c1;
// Now c1 and c2 both reference the same object.
set(c2, 42);
set(c1, 43);
// Now they both reference an object with value 43.
}
要创建一个新的 GcRef<T>
,调用 GcRef::new(e)
,其中 e
是一个表达式,其值你想在 GC 堆上。
高级使用
如果您需要从GC堆中删除数据,您可以使用GcNullableRef
而不是GcRef
。您可以使用Gc::new_nullable
来创建一个。 GcNullableRef
类似于GcRef
,但增加了一个remove
方法。第一次调用remove
将返回一个填充了之前在GC堆中的数据的Option
。后续对remove
的调用将返回None。
安全性
Bronze的早期版本允许用户获取GC对象的多个可变引用。这现在不应再成为可能;相反,Bronze动态跟踪借用(使用与RefCell中使用的机制非常相似的机制)。要获取GC对象的不可变或可变借用引用,请在GcRef
上调用borrow()
或borrow_mut()
。
实验性实现
此实现是实验性的。特别是,收集器将不会运行;请注意,您最终会耗尽内存。然而,当前版本适合实验和原型设计。
依赖项
~0–2.1MB
~41K SLoC