c+;=map(lambda n:n*2,c)杀死Python 3外壳。为什么?

c+;=map(lambda n:n*2,c)杀死Python 3外壳。为什么?,python,python-3.x,python-2.7,Python,Python 3.x,Python 2.7,然而,Python2也是如此,在Python3中,map生成的列表不同于生成器。那么为什么c+=map(lambda n:n*2,范围(1,3))起作用呢?c+=foo的等价物是否与c=c.\uu iadd\uuuo(foo)。如果c是一个列表,则list.\uuuuu iadd\uuuu方法接受任何iterable,包括生成器表达式: Python 3.6.4 (v3.6.4:d48ecebad5, Dec 18 2017, 21:07:28) [GCC 4.2.1 (Apple Inc. b

然而,Python2也是如此,在Python3中,map生成的列表不同于生成器。那么为什么
c+=map(lambda n:n*2,范围(1,3))
起作用呢?

c+=foo
的等价物是否与
c=c.\uu iadd\uuuo(foo)
。如果
c
是一个列表,则
list.\uuuuu iadd\uuuu
方法接受任何iterable,包括生成器表达式:

Python 3.6.4 (v3.6.4:d48ecebad5, Dec 18 2017, 21:07:28)
[GCC 4.2.1 (Apple Inc. build 5666) (dot 3)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> c = [1, 2]
>>> c += map(lambda n: n *2, range(1, 3))
>>> c
[1, 2, 2, 4]
>>> c = [1, 2]
>>> c += map(lambda n: n *2, c)
Killed!
即使
列表。\uuuuu add\uuuuu
不支持生成器表达式,也会出现此问题:

>>> x = []
>>> x += (i for i in range(3))
>>> x
[0, 1, 2]
(荣誉)

Python2版本的工作原理正是因为
map
将在调用
c.\uuu iadd\uuu
之前创建一个列表;包含2个元素的新列表将传递给
c.\uu iadd\uu
。同样地,
c+=map(lambda n:n*2,range(1,3))
也可以工作,因为在Python 2中
range(1,3)
将创建一个新列表,在Python 3中它将创建一个range-sequence对象,两者都是不同的

如果用生成器表达式替换
map
,也可以触发Python 2中的病理行为:

for elem in c:
    c.append(elem * 2)
for elem in c:
    c.append(elem * 2)
Python 2.7.15rc1 (default, Nov 12 2018, 14:31:15) 
[GCC 7.3.0] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> x = [1, 2]
>>> x += (n * 2 for n in x)