当我使用生成器时,即使我修改传递给它的字典,生成器仍然会给我一个旧数据结构的结果。 我怎么能解决这个问题?
def min_key_order(adict:dict):
for key, value in sorted(adict.items()):
yield (key, value)
d = {1:'a', 2:'x', 4:'m', 8:'d', 16:'f'}
i = min_key_order(d)
print(next(i))
d.pop(2)
print(next(i))
它给了我(1,'a')
,(2,'x')
,即使我从字典中弹出了密钥2。
答案 0 :(得分:2)
您的生成器没有迭代字典。它正在迭代sorted()
返回的新列表对象:
>>> d = {1:'a', 2:'x', 4:'m', 8:'d', 16:'f'}
>>> l = sorted(d.items())
>>> d
{1: 'a', 2: 'x', 4: 'm', 8: 'd', 16: 'f'}
>>> l
[(1, 'a'), (2, 'x'), (4, 'm'), (8, 'd'), (16, 'f')]
>>> d.pop(2)
'x'
>>> l
[(1, 'a'), (2, 'x'), (4, 'm'), (8, 'd'), (16, 'f')]
从字典中删除项目无法更新新列表;该结构不是字典上的实时视图。
要实现这一点,您必须每次迭代重新排序字典,并跟踪迭代位置:
def sorted_view(d):
pos = 0
while pos < len(d):
yield sorted(d.items())[pos]
pos += 1
这非常低效;分拣是一种相对昂贵的操作。
更有效的方法是按排序顺序存储密钥,然后如果密钥仍然可用,则 test :
def min_key_order(adict:dict):
for key in sorted(adict):
if key in adict:
yield (key, adict[key])
但是,如果您添加更多密钥,则无法检测到。