15

我有一个列表说mysolution

>>>mySolution
[[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]
>>> mySolution[0][0] = 1    
>>> mySolution
[[1, 0, 0, 0], [1, 0, 0, 0], [1, 0, 0, 0], [1, 0, 0, 0]]

预期输出:

[[1, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]

为什么我的列表中的所有第一个元素都被更改为 1?我只想将第一个列表的第一个元素更改为 1。

4

4 回答 4

19

重要的是您如何创建原始mysolution列表。看起来,它包含四次相同的列表,这就是为什么更改一次会使其在所有四个位置都发生更改的原因。

要像这样初始化独立的零填充列表,您可以执行以下操作:

mysolution = [[0] * 4 for i in range(4)]
于 2013-09-22T17:34:22.840 回答
8

您很可能创建了这样的列表:

mySolution = [0]*4
mySolution = [mySolution]*4

或等效地:

mySolution = [[0]*4]*4

上述任何一个片段都将创建一个包含四个子列表的列表,这些子列表是完全相同的 sublist的副本,因此对一个子列表的任何修改都将反映在其他子列表上——它们是相同的。解决方案是创建四个不同的子列表:

mySolution = [[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]

或者更短一点:

mySolution = [[0]*4 for _ in xrange(4)]
于 2013-09-22T17:37:42.713 回答
3

因为所有包含的列表实际上都是同一个列表。当你这样做时:

l = [0, 0, 0, 0]
my_solution = [l, l, l]

然后,my_solution[0]my_solution[1], 和my_solution[2]是对同一个对象 ( l) 的引用。

如果您在一个位置修改列表,它会随处更改。那是因为列表是可变对象。

相反,使用多个列表:

l1 = [0, 0, 0, 0]
l2 = [0, 0, 0, 0]
l3 = [0, 0, 0, 0]
my_solution = [l1, l2, l3]

这将按预期工作。

于 2013-09-22T17:31:27.783 回答
3

请注意,这很好:

mySolution = [[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]
mySolution[0][0] = 1    
print mySolution

>>> 
[[1, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]

这一切都取决于你如何初始化你的solution. 这个

mySolution = [[0, 0, 0, 0]]*4
mySolution[0][0] = 1    
print mySolution

>>> 
[[1, 0, 0, 0], [1, 0, 0, 0], [1, 0, 0, 0], [1, 0, 0, 0]]
>>> 

因为这里的每个数组都是[0, 0, 0, 0]in初始化数组的mySolution副本。如果您更改第一个数组的第一个元素,它的副本也会更改。[0, 0, 0, 0][[0, 0, 0, 0]]*4

通过此初始化mySolution = [[0, 0, 0, 0] for x in range(4)],您不会复制数组而是追加[0,0,0,0]四次,从而得到您期望的结果。

于 2013-09-22T17:52:47.803 回答