LIST.append(1)和LIST = LIST + [1]有什么区别(Python)

8 投票
4 回答
6039 浏览
提问于 2025-04-16 03:41

当我在交互式命令行中执行这些语句时,我得到了这个结果:

L=[1,2,3]
K=L

L.append(4)

L
[1,2,3,4]
K
[1,2,3,4]

但是当我把 L.append(4) 替换成 L = L + [4] 时,我得到了:

L
[1,2,3,4]
K
[1,2,3]

这是不是某种引用的问题?为什么会这样?

我还注意到一个有趣的事情,就是 L += [4] 的表现像 .append,这很奇怪,因为我以为它会像 L = L + [4] 那样。

如果能对这些内容做进一步的解释,我会非常感激。

谢谢

4 个回答

1

如果你对字节码感兴趣的话:

>>> def L_app( ):
...     L.append( 4 )
...
>>> def L_add( ):
...     L = L + [ 4 ]
...
>>> def L_add_inplace( ):
...     L += [ 4 ]
...
>>> dis.dis( L_app )
  2           0 LOAD_GLOBAL              0 (L)
              3 LOAD_ATTR                1 (append)
              6 LOAD_CONST               1 (4)
              9 CALL_FUNCTION            1
             12 POP_TOP
             13 LOAD_CONST               0 (None)
             16 RETURN_VALUE
>>> dis.dis( L_add )
  2           0 LOAD_FAST                0 (L)
              3 LOAD_CONST               1 (4)
              6 BUILD_LIST               1
              9 BINARY_ADD
             10 STORE_FAST               0 (L)
             13 LOAD_CONST               0 (None)
             16 RETURN_VALUE
>>> dis.dis( L_add_inplace )
  2           0 LOAD_FAST                0 (L)
              3 LOAD_CONST               1 (4)
              6 BUILD_LIST               1
              9 INPLACE_ADD
             10 STORE_FAST               0 (L)
             13 LOAD_CONST               0 (None)
             16 RETURN_VALUE
2

使用 append 的时候,你是在直接修改这个列表。而用 L=L+[4] 的话,你其实是先复制了原来的 L,然后加上一个新元素,最后再把这个结果赋值回 L,这样就让 LK 不再相等了。

我对 += 的行为不太确定。

16
L.append(4)

这段代码是在现有列表 L 的末尾添加一个元素。

L += [4]

+= 这个符号会调用一个叫做 __iadd__() 的神奇方法。实际上,列表(list)重写了这个方法,使它的功能和 extend() 一样。extend()append() 一样,都是直接把元素添加到已有的列表中。

L = L + [4]

L + [4] 会生成一个新列表,这个新列表是在 L 的基础上加上了 4。这个 列表随后被重新赋值给 L。因为你创建了一个新的列表对象,所以 K 不会受到这个赋值的影响。

我们可以使用 id() 来查看何时创建了一个新的对象引用:

>>> L = [1, 2, 3]
>>> id(L)
152678284
>>> L.append(4)
>>> id(L)
152678284

>>> L = [1, 2, 3]
>>> id(L)
152680524
>>> L = L + [4]
>>> id(L)
152678316

撰写回答