我正在使用Python 3并使用此代码:
import random
mat = [[0]*5]*5
for i in range (0,5) :
for j in range (0,5) :
mat[i][j] = random.randint(10,50)
print (mat)
我得到的结果如下:
[[26, 10, 28, 21, 15], [26, 10, 28, 21, 15], [26, 10, 28, 21, 15], [26, 10, 28, 21, 15], [26, 10, 28, 21, 15]]
行彼此相等,但循环似乎没问题。
有什么问题?
答案 0 :(得分:4)
因为所有内部列表实际上都是同一对象的副本,所以修改其中一个 也将自动影响其他列表。:
>>> l = [[0]*5]*5
>>> [id(x) for x in l]
[155011468, 155011468, 155011468, 155011468, 155011468]
相同的ID意味着所有索引实际上都指向列表中的同一个对象:
>>> l[0][0] = 1 #modifying one, changes all of them
>>> l
[[1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0]]
使用list comprehension
解决此问题:
>>> l = [[0]*5 for _ in xrange(5)]
>>> [id(x) for x in l] #all lists are unique now
[155710028, 155710764, 155710700, 155710732, 155709996]
按预期工作:
>>> l[0][0] = 1
>>> l
[[1, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]
答案 1 :(得分:1)
问题在于这一行:
mat = [[0]*5]*5
这样做是为了创建一个包含5个零([0]*5
)的列表,然后再创建5个对相同列表的引用。
解决这个问题的解决方案:
mat = [[0]*5 for _ in xrange(5)]
这将创建一个5个零的列表,分别为5个单独的时间,这意味着所有列表都是独立的。