无法清除字典列表
Cannot clear a list of dictionaries
一个对象有一个字典列表:
self.aggregator = []
self.aggregator.append({'type': 'Log', 'entry': logline1})
self.aggregator.append({'type': 'Log', 'entry': logline2})
print self.aggregator
到目前为止一切正常:
[{'type': 'Log', 'entry': 'Content of logline 1'}, {'type': 'Log', 'entry': 'Content of logline 2'}]
然后我尝试使用不同的方法重置此列表的内容:
self.aggregator = []
del self.aggregator
现在当我打印列表时它是空的:
[]
但是当我检查列表的长度时,它仍然是原来的大小:
>> print len(self.aggregator)
2
为什么这是可能的,我错过了什么吗?
===更新
下面是完整的演示代码。我想出了导致错误的原因。这是带有 "del self.aggregator" 的行。当我删除此行时,一切都按预期进行。使用 Python 2.7.10 和 Python 2.7.11(32 位)在 OS X 上测试此行为 Windows 7.
class Checker(object):
aggregator = []
aggregator_max = 10
def __init__(self):
pass
def finalizeAggregator(self):
string = "\n".join([attribute['string'] for attribute in self.aggregator])
# Check for a match on all the aggregator content
match_result = self.checkString(string,"")
if match_result:
# If match has been found, check the aggregator contents one by one
for element in self.aggregator:
self.checkString(element["string"],
element["module"],
use_aggregator=False)
# Clear aggregator
print self.aggregator
self.aggregator = None
self.aggregator = []
del self.aggregator
print self.aggregator
print len(self.aggregator)
def checkString(self, string, module, use_aggregator=False):
# If aggregator should be used
if use_aggregator:
print "USING aggregator"
# As long as the aggregator is not full
if len(self.aggregator) <= self.aggregator_max:
#if string not in self.aggregator:
# Add element to aggregator
self.aggregator.append({"string": string,
"module": module})
# Process aggregator if full
if len(self.aggregator) >= self.aggregator_max:
self.finalizeAggregator()
# Otherwise return
else:
return False
else:
print "NOT using aggregator"
if "evil" in string:
print "WARNING!!!"
if __name__ == '__main__':
checker = Checker()
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is evil', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
您将 aggregator
定义为 class 属性;在您直接分配给 self.attribute
之前,它是一个 shared class 属性。但是当你这样做时:
self.aggregator = None
那 auto-vivifies 一个 实例 属性。所以在那之后,它是一个完全不同的变量,它隐藏(隐藏)了 class 属性。除了当您执行 del self.aggregator
时,您删除实例属性,并取消隐藏 class 属性,看到原始(共享)值。
如果目标是拥有实例属性,请使用实例属性。变化:
class Checker(object):
aggregator = []
aggregator_max = 10
def __init__(self):
pass
至:
class Checker(object):
aggregator_max = 10
def __init__(self):
self.aggregator = []
并且它只是一个实例变量(如果您打算稍后使用它,请不要 del
实际属性,这是荒谬的;分配空的 list
没问题)。
请注意,分配空 list
(替换 self.aggregator
中保留的 reference)和删除 之间存在差异contentslist
of the list
referenced by self.aggregator
(del self.aggregator[:]
or in Py3.3+, self.aggregator.clear()
) 在可能有多个引用的情况下到 self.aggregator
引用的 list
。查看 Clearing Python lists 了解更多详情。
一个对象有一个字典列表:
self.aggregator = []
self.aggregator.append({'type': 'Log', 'entry': logline1})
self.aggregator.append({'type': 'Log', 'entry': logline2})
print self.aggregator
到目前为止一切正常:
[{'type': 'Log', 'entry': 'Content of logline 1'}, {'type': 'Log', 'entry': 'Content of logline 2'}]
然后我尝试使用不同的方法重置此列表的内容:
self.aggregator = []
del self.aggregator
现在当我打印列表时它是空的:
[]
但是当我检查列表的长度时,它仍然是原来的大小:
>> print len(self.aggregator)
2
为什么这是可能的,我错过了什么吗?
===更新
下面是完整的演示代码。我想出了导致错误的原因。这是带有 "del self.aggregator" 的行。当我删除此行时,一切都按预期进行。使用 Python 2.7.10 和 Python 2.7.11(32 位)在 OS X 上测试此行为 Windows 7.
class Checker(object):
aggregator = []
aggregator_max = 10
def __init__(self):
pass
def finalizeAggregator(self):
string = "\n".join([attribute['string'] for attribute in self.aggregator])
# Check for a match on all the aggregator content
match_result = self.checkString(string,"")
if match_result:
# If match has been found, check the aggregator contents one by one
for element in self.aggregator:
self.checkString(element["string"],
element["module"],
use_aggregator=False)
# Clear aggregator
print self.aggregator
self.aggregator = None
self.aggregator = []
del self.aggregator
print self.aggregator
print len(self.aggregator)
def checkString(self, string, module, use_aggregator=False):
# If aggregator should be used
if use_aggregator:
print "USING aggregator"
# As long as the aggregator is not full
if len(self.aggregator) <= self.aggregator_max:
#if string not in self.aggregator:
# Add element to aggregator
self.aggregator.append({"string": string,
"module": module})
# Process aggregator if full
if len(self.aggregator) >= self.aggregator_max:
self.finalizeAggregator()
# Otherwise return
else:
return False
else:
print "NOT using aggregator"
if "evil" in string:
print "WARNING!!!"
if __name__ == '__main__':
checker = Checker()
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is evil', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
checker.checkString('This is benign', 'test', use_aggregator=True)
您将 aggregator
定义为 class 属性;在您直接分配给 self.attribute
之前,它是一个 shared class 属性。但是当你这样做时:
self.aggregator = None
那 auto-vivifies 一个 实例 属性。所以在那之后,它是一个完全不同的变量,它隐藏(隐藏)了 class 属性。除了当您执行 del self.aggregator
时,您删除实例属性,并取消隐藏 class 属性,看到原始(共享)值。
如果目标是拥有实例属性,请使用实例属性。变化:
class Checker(object):
aggregator = []
aggregator_max = 10
def __init__(self):
pass
至:
class Checker(object):
aggregator_max = 10
def __init__(self):
self.aggregator = []
并且它只是一个实例变量(如果您打算稍后使用它,请不要 del
实际属性,这是荒谬的;分配空的 list
没问题)。
请注意,分配空 list
(替换 self.aggregator
中保留的 reference)和删除 之间存在差异contentslist
of the list
referenced by self.aggregator
(del self.aggregator[:]
or in Py3.3+, self.aggregator.clear()
) 在可能有多个引用的情况下到 self.aggregator
引用的 list
。查看 Clearing Python lists 了解更多详情。