当`gc.garbage`为空时,垃圾收集段错误在python代码中

时间:2015-10-24 03:36:26

标签: python garbage-collection segmentation-fault cython garbage

以下代码正常运行并打印出空列表(在python3.4上):

import gc
# code interfacing with C and cython
print(gc.garbage, flush=True)

将此行添加到最后会使其成为段错误:

gc.collect()

似乎纯粹的运气是自动收集不会自行发生(我花了一些时间来获得可重现的错误)。该系列未在"程序结束时运行"或者是因为我以交互方式运行它。

一些谷歌搜索让我相信一些C / Cython代码正在创建/销毁对象而不告诉python这些对象已经从内存中删除。然后python尝试删除它们并崩溃。

我如何找到这些物品是什么?我认为在崩溃诱导gc.garbage之前它们会在gc.collect()

或者我的假设完全不正确?

在此代码前加gc.set_debug(gc.DEBUG_STATS | gc.DEBUG_LEAK)会导致python异常,而不是段错误。

---> print(gc.garbage, flush=True)
     gc.collect()
...
ReferenceError: weakly-referenced object no longer exists

编辑:在其中一个答案的评论后更改/简化

1 个答案:

答案 0 :(得分:1)

您可能误解了gc.garbagegc.disable()gc.disable()关闭循环垃圾收集器,只保留引用计数内存管理。即使垃圾收集器关闭,也没有一些单独的“垃圾检测器”可以检测循环垃圾;垃圾检测是垃圾收集器的工作。

此外,gc.garbage仅填充了GC无法清除的特定种类的奇怪垃圾。大多数垃圾都不会在那里结束。

至于你如何调试这个,我不熟悉你使用的工具。像Valgrind这样的通用工具可能很有用,像gc.DEBUG_LEAK这样的GC标记可能会有所帮助。