Short Story: Why and in what way is the list [2*[0]]*2
different from the list[[0, 0], [0, 0]]
?
Long Story:
I was trying to do one of the Python Morsels exercises. Very simply: add all values of the same position in multiple lists of lists. The Example given in the question was:
matrix1 = [[1, -2], [-3, 4]]
matrix2 = [[2, -1], [0, -1]]
>>> add(matrix1, matrix2)
[[3, -3], [-3, 3]]
So I gave it a shot and wrote the following code:
def addmorsel(*inputslists):
addlist = [len(inputslists[0][0])*[0]]*len(inputslists[0])
for listoflists in inputslists:
for i,onelist in enumerate(listoflists):
for j,value in enumerate(onelist):
addlist[i][j] = addlist[i][j] + value
return addlist
But when I use this function on the example matrices it returns
[[0, 0], [0, 0]]
instead of the right answer. So I printed the returned addlist
to see what happens and apparently the line addlist[i][j] = addlist[i][j] + value
seems to add the value to every list within a list instead of only the list it is referencing to.
Replacing the addlist creation line addlist = [len(inputslists[0][0])*[0]]*len(inputslists[0])
by addlist = [[0,0],[0,0]] seems to do the job, but I do not understand why, because that is exactly the same as what addlist becomes by the previous line.
I thought: maybe it references the previous list or something, so I also tried addlist = [2*[0]]*2
,so replacing the len() functions by their output, but somehow that also gives the wrong answer.
So my basic understanding of python lists is being shook here.
Why is [2*[0]]*2
different from [[0, 0], [0, 0]]
?