回到另一个关于Rust的基本设计决策的noob问题。
我正在写一个简单的小游戏。我在他们的“id”键入的数据结构中有一个游戏对象池。我的问题是如何处理与池中对象有关系的其他结构(比池中的结构更短)。
起初我做了以下事情:
struct Foo<'a> {
game_obj: &'a GameObject
// etc.
}
但是当我试图(可变地)引用({1}}与现存GameObject
相同的范围时,我遇到了一些借用检查器的问题。
所以现在我正在考虑这样的事情:
Foo
这可能有其他问题,但它确实解决了struct Foo {
game_obj_id: uint,
// etc.
}
“垄断”引用其相关Foo
的能力的直接问题。
通常采用哪些方法?
答案 0 :(得分:2)
您可以在Rc<RefCell<GameObject>>
中存储struct
(除非GameObject
是特征,在这种情况下,在实施动态大小类型(DST)之前,这将无效。)< / p>
RefCell<T>
是一种类型,其中包含T
和一个标志,用于指示该值是否已被可靠地借用,是否已被无限借用或尚未借入。 RefCell
基本上是在运行时而不是在编译时移动借位检查;如果违反借用规则(如果已经可变地或不可变地借入,则不能进行可变借款;如果已经可变地借入,则不能进行不可变借款),任务将失败。请注意,可以同时存在多个不可变借用。
Rc<T>
是一种类型,包含指向T
的指针和引用计数(实际上是两个:强引用计数和弱引用计数)。您可以.clone()
Rc
来增加引用计数而不克隆基础对象。删除Rc
时,引用计数减少。当引用计数降至零时,将丢弃引用对象并回收内存。请注意Rc
已经动态分配内存;没有必要使用Rc<Box<Thing>>
之类的结构(除非你知道你在做什么)。
还有Weak<T>
,可以代替Rc
用于不需要保持对象存活的引用。