python如何更改子列表元素的值?

python如何更改子列表元素的值?,python,sublist,Python,Sublist,我有以下代码: matrix = [[0] * 3] * 3 matrix[0][0] = 2 我希望得到以下结果: [[2, 0, 0], [0, 0, 0], [0, 0, 0]] 但是,它会更改每个子列表的第一个元素并返回此列表: [[2, 0, 0], [2, 0, 0], [2, 0, 0]] 如果我将矩阵定义为: matrix = [[0, 0, 0], [0, 0, 0], [0, 0, 0]] 然后它就起作用了 有谁能告诉我,为什么会这样,如何解决这个问题 感谢发生这种情

我有以下代码:

matrix = [[0] * 3] * 3
matrix[0][0] = 2
我希望得到以下结果:

[[2, 0, 0], [0, 0, 0], [0, 0, 0]]
但是,它会更改每个子列表的第一个元素并返回此列表:

[[2, 0, 0], [2, 0, 0], [2, 0, 0]]
如果我将矩阵定义为:

matrix = [[0, 0, 0], [0, 0, 0], [0, 0, 0]]
然后它就起作用了

有谁能告诉我,为什么会这样,如何解决这个问题


感谢

发生这种情况是因为
[[0]*3]*3
实际上正在创建一个由3个相同对象组成的数组(即
[0]*3
数组)。一种方法是创建一次内部数组并进行复制。另一种方法是使用
[[0]*3表示xrange(3)]中的x
,因为这会在列表理解中执行
[0]*3
,每次都创建一个新数组。

Python通过指针而不是值*赋值,这有时会导致不希望的结果,比如这个结果。这里有一个教程解释了真正发生的事情:这里有一个可能的修复方法


*(正如已经指出的,这是不完全正确的,但是它的结果类似于我更熟悉的C等其他语言中发生的情况,如果您将指针传递给变量,而不是变量值的副本。)

这是您的问题,在本例中,
矩阵
,基本上与:

>>> a = [0,0,0]
>>> matrix1 = [a,a,a]
这意味着当您执行
matrix1[0][0]=2
时,Python所做的是跟随位于
matrix1
第一个索引处的指针,该指针指向对象
a
,然后查看位于
a
第一个索引处的指针,该指针读取
0
,然后将其更改为
2
。然后,当您要求它计算
matrix1
时,它会查找
a
三次,每次都会找到
[2,0,0]


在我上面有一个,使用列表理解来强制创建新对象,而不是为已经存在的对象添加指针。这可能会更好地为您服务:)

可变对象上的列表乘法会创建对象引用的副本,而不是不同对象的副本。这是一个相当常见的问题。。。解决方案是使用列表理解<代码> [[ 0 ] * 3,用于范围(3)] /代码>,您可能还需要考虑使用多维数组类型或矩阵类型,如<代码> NDAREX 或<代码>矩阵< /代码>,而不是列表列表。(即使您只是出于学习目的而这样做,学习如何构建类似于
np.matrix
的简单版本的东西也是一个很好的开始…)Amazing,确实要感谢大家的快速回答、解释和解决方案。“Python按指针赋值”是一种非常误导人的说法。Jython和PyPy当然不会分配任何指针,因为它们是用语言(Java和(R)编写的)Python没有指针…实际上Java几乎是所有的指针。任何引用类型的变量实际上只是一个伪装的指针。如果Java有类似的语法,它也会有同样的问题。现在我有一个进一步的问题:为什么子列表的元素不是同一对象的副本,尽管您创建了子列表元素在运行这两行之后,矩阵=[[0]*3代表x范围内的x(3)]矩阵[0][0]=2,我希望得到这个结果:[[2,2,2],[0,0,0],[0,0]].为什么我的想法是错误的?我想,我明白了:可能原因是,因为子列表的元素是int类型的,所以它们是不可变的,被创建为新对象,而不是引用列表中的同一对象。