为什么__del__没有正常工作

时间:2012-08-16 15:42:08

标签: python class

我认为这是访谈中最常见的问题:

class A:
     def __init__(self, name):
          self.name = name
     def __del__(self):
          print self.name,

aa = [A(str(i)) for i in range(3)]
for a in aa:
    del a

这个代码的输出是什么以及为什么。 输出将是什么,为什么? 那是因为a是对列表中的对象的引用然后我们调用del方法我们删除这个引用而不是对象吗?

3 个答案:

答案 0 :(得分:5)

至少有2个引用a引用的对象(变量是引用到对象,它们本身不是对象)。列表中有一个引用,然后是引用“a”。当您del a时,删除一个引用(变量a),但不删除列表中的引用。

另请注意,Python不保证将__del__被调用...

答案 1 :(得分:4)

当一个对象被销毁时,会调用

__del__;这将在从程序的可访问内存中删除对象的最后一个可能引用之后发生。根据实施情况,这可能会立即发生,也可能会在一段时间后发生。

您的代码只是从执行范围中删除了本地名称a;对象仍保留在列表中,因此仍可访问。例如,尝试编写del aa[0]

答案 2 :(得分:3)

来自文档:

  

注意del x不直接调用x.__del__() - 前者将x的引用计数递减1,而后者仅在x的引用计数达到零时调用。

当垃圾收集器找到要销毁的对象时,会触发

__del__。垃圾收集器将尝试销毁引用计数为0的对象。del只是解耦本地命名空间中的标签,从而减少解释器中对象的引用计数。垃圾收集器的行为在很大程度上被认为是解释器的实现细节,因此无法保证对象的__del__将以任何特定顺序调用,甚至根本不会。这就是为什么这段代码的行为是未定义的。