垃圾收集器缺少列表中的最后一个值
Garbage collector missing last value in list
在测试包含弱引用的 class 时,我偶然发现了这个稍微奇怪的行为:Python 垃圾收集器似乎缺少列表中的最后一个元素。一个最小的例子:
class Test(object):
def __init__(self, i):
self.i = i
def __del__(self):
print('Deleting Test {0}'.format(self.i))
if __name__ == '__main__':
x = [Test(i) for i in range(5)]
for t in x:
print(t.i)
x = []
以上将打印:
0
1
2
3
4
Deleting Test 3
Deleting Test 2
Deleting Test 1
Deleting Test 0
无论创建对象列表的大小(10、100、1000 等)如何,都会发生这种情况。为了仔细检查是否是这种情况,我尝试强制进行垃圾回收,并确保在将原始列表设置为 [=13 后仍然可以使用对原始列表值的弱引用(并且未标记为死) =] 或调用 del x
:
import weakref
import gc
z = None
if __name__ == '__main__':
x = [Test(i) for i in range(5)]
for t in x:
print(t.i)
z = weakref.ref(x[4])
x = []
gc.collect(2)
print(z().i)
此外,尝试创建一个大列表以(再次)强制垃圾收集无济于事;例如,在上面的 x = []
和 gc.collect(2)
之间插入以下内容:
p = [i for i in range(10000000)]
这发生在 Python 2.7.6 和 3.3.3 上。我意识到垃圾收集是不确定的,但这似乎很可疑。是否存在最后一个元素未被垃圾回收的特定原因,或者这是某种偏离一个的错误?
您的第一个源代码中的变量 t
仍然存在,并且包含对最后一个条目的引用。在您调用 del t
之后,最后一个 Test
对象将被删除。
在测试包含弱引用的 class 时,我偶然发现了这个稍微奇怪的行为:Python 垃圾收集器似乎缺少列表中的最后一个元素。一个最小的例子:
class Test(object):
def __init__(self, i):
self.i = i
def __del__(self):
print('Deleting Test {0}'.format(self.i))
if __name__ == '__main__':
x = [Test(i) for i in range(5)]
for t in x:
print(t.i)
x = []
以上将打印:
0
1
2
3
4
Deleting Test 3
Deleting Test 2
Deleting Test 1
Deleting Test 0
无论创建对象列表的大小(10、100、1000 等)如何,都会发生这种情况。为了仔细检查是否是这种情况,我尝试强制进行垃圾回收,并确保在将原始列表设置为 [=13 后仍然可以使用对原始列表值的弱引用(并且未标记为死) =] 或调用 del x
:
import weakref
import gc
z = None
if __name__ == '__main__':
x = [Test(i) for i in range(5)]
for t in x:
print(t.i)
z = weakref.ref(x[4])
x = []
gc.collect(2)
print(z().i)
此外,尝试创建一个大列表以(再次)强制垃圾收集无济于事;例如,在上面的 x = []
和 gc.collect(2)
之间插入以下内容:
p = [i for i in range(10000000)]
这发生在 Python 2.7.6 和 3.3.3 上。我意识到垃圾收集是不确定的,但这似乎很可疑。是否存在最后一个元素未被垃圾回收的特定原因,或者这是某种偏离一个的错误?
您的第一个源代码中的变量 t
仍然存在,并且包含对最后一个条目的引用。在您调用 del t
之后,最后一个 Test
对象将被删除。