C++垃圾回收和循环引用数据

4

我目前正在使用引用计数技术(在C++中)实现垃圾收集器。然而,存在一个主要问题,即如果数据存在循环引用,它们永远不会被收集,因为它们的引用计数始终为非零。

我尝试搜索并发现了这些称为追踪垃圾收集器、标记-清除算法等的东西。我能否实现其中之一?它们到底是如何工作的?


2
研究弱引用。此外,请尽量避免循环引用。 - Cat Plus Plus
这不是一个很好的问题。当然你可以实现一个,你应该查阅一本好的编程语言书籍来了解那些垃圾回收算法是如何工作的。 - Michael Price
@Michael Price:到目前为止,我找到的大多数资源只是不停地解释各种术语,但没有一个真正费心给出一些例子。我真的不关心操作系统、编译器或Java语言如何收集垃圾,我关心的是我如何自己做到。但到目前为止,没有什么成功的经验。正如问题中提到的,引用计数并不能准确地收集所有的垃圾。 - IcySnow
4
“@Cat:“此外,请尽量避免完全使用循环引用”:垃圾收集器不应该对程序员施加限制!” - TonyK
我相信它是可以实现的,但我不确定你是否真的想这样做 :) - ScarletAmaranth
显示剩余5条评论
2个回答

3
这是垃圾回收器设计中的经典问题。请查看维基百科上的垃圾回收文章,它在呈现垃圾回收器设计中不同权衡方面方面非常好。像三色标记这样的“更进化”的算法实际上相当简单易于实现。我已经使用了这些指令,在C中为自己的Lisp实现实现了一个跟踪收集器。
在追踪垃圾回收器中最复杂的处理是遍历对象树(例如找到对“活动”对象的引用)。如果您正在为另一种语言编写解释器,则这并不太难,因为您可以在根对象类(或所有对象的其他公共分母)中连接此设施。但是,如果您正在为C ++编写C ++的垃圾回收器,那么您将很难做到这一点,因为您需要检查对象内容以查找指向内存的其他分配区域的指针。

如果您出于教育目的编写垃圾回收器,我建议您考虑编写另一种语言(没有直接访问指针的语言)的解释器。如果您想在生产软件中使用C++编写垃圾回收器,我强烈建议您使用现有的高质量生产实现


链接已失效,请更新。 - Javid
1
@Javid 链接已更新! - André Caron

1

http://www.boost.org/doc/libs/1_48_0/libs/smart_ptr/weak_ptr.htm

weak_ptr类模板存储对已由shared_ptr管理的对象的“弱引用”。要访问对象,可以使用shared_ptr构造函数或成员函数lock将weak_ptr转换为shared_ptr。当指向该对象的最后一个shared_ptr消失并且删除对象时,尝试从引用已删除对象的weak_ptr实例获取shared_ptr将失败:构造函数将抛出类型为boost :: bad_weak_ptr的异常,而weak_ptr :: lock将返回一个空shared_ptr。
实际上,你不应该有循环引用,但如果你正在处理无法重构它们的设计(这偶尔会发生),请尝试在其中一个方向上放置weak指针,以便它们不会阻止销毁。

如果您正在管理没有垃圾收集器的资源,这是一个很好的建议,但对于OP实现垃圾收集器并没有帮助。 - Mike Seymour
+1 - 这个答案很有用,可以轻松解决字面问题背后的问题。 - Andy Thomas
是的,我正在尝试解决当前GC存在的问题。因为如果用户使用它来控制诸如循环链表之类的东西,那么它就会出错。 - IcySnow
-1 对于 +1 的偏移量:这很少是可行的解决方案,并且在许多数据结构(图形等)中循环是隐含的。 - James Kanze
@user1065635 - 你(或者你的团队)是最终用户还是有外部用户? - Andy Thomas

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接