在循环字典时删除和添加键

时间:2017-07-11 06:51:55

标签: python dictionary for-loop

我有一本字典,我想从字典中删除一个密钥并将其更改为其他内容。但是,当我在字典中循环时,我不明白的最后一个键会发生奇怪的事情。

这里我在删除密钥之前和之后打印密钥并在其位置添加新密钥

from operator import add

x = {(19,2):0, (1,1):1, (10,1):2, (5,5):3}
y = (1, 0)

for i in x.values():

    newDir = tuple(map(add, x.keys()[i], y))
    print x.keys()[i]
    x.pop( x.keys()[i] )
    x[newDir] = i

    print x.keys()[i]
    print i
    print ' '

这会产生以下结果:

(19, 2)
(20, 2)
0

(1, 1)
(2, 1)
1

(10, 1)
(2, 1)
2

(11, 1)
(2, 1)
3

注意值3的键不是(5,5)而是(11,1),并且在弹出并添加新密钥后,它应该是(6,5)而不是(2,1)。我不知道(11,1)来自哪里以及为什么(2,1)在值2和3中重复。

正确的输出是

(19, 2)
(20, 2)
0

(1, 1)
(2, 1)
1

(10, 1)
(11, 1)
2

(5, 5)
(6, 5)
3

1 个答案:

答案 0 :(得分:1)

字典是无序的,每当您添加/删除密钥时,它们的明显顺序可能会发生变化。这意味着x.keys()[i]无法保证为您提供正确的密钥(至少在您通过添加或删除密钥更改x之后)。因为在您弹出并添加新密钥后,订单可能已更改,这意味着x.keys()[i] 可能会从字典中提供任何密钥。

例如在你的输出中

  • 为第一个工作:(19, 2) - > (20, 2)
  • 它也适用于第二个:(1, 1) - > (2, 1)
  • 第三个开始失败:(10, 1) - > (2, 1)!找到并修改了正确的密钥,但显而易见的是"结果是值1
  • 的结果
  • 对于第四个问题,所有事情都发生了变化:(11, 1)是值2之后的关键字,它已被更改,显而易见的结果是值1的关键字。

因此,您应该创建一个新词典,而不是在原地更改它:

from operator import add

x = {(19,2):0, (1,1):1, (10,1):2, (5,5):3}
y = (1, 0)
newx = {}

for key, value in x.items():
    print(key)

    newDir = tuple(map(add, key, y))
    newx[newDir] = value

    print(newDir)
    print(value)
    print(' ')

print(newx)

产生预期的输出:

(19, 2)
(20, 2)
0

(1, 1)
(2, 1)
1

(10, 1)
(11, 1)
2

(5, 5)
(6, 5)
3

{(20, 2): 0, (11, 1): 2, (6, 5): 3, (2, 1): 1}