Python中的变量创建过程

时间:2016-10-14 19:02:26

标签: python arrays python-2.7

在Microsoft shell中执行所有操作并使用2.7.12

前奏

a = [1,2,3,4,5]
b = [1,2,3,4,5]
c = a

操作

a[0] is b[0] is c[0]
True

三个列表是否指向内存位置中的相同元素?如果改变了,可能会改变吗?

第一部分理解:

c[0] = 8888888
a[0]
8888888

第一部分我不明白:

b[0] = 9999999
a[0]
1

3 个答案:

答案 0 :(得分:3)

Python可以决定共享不可变对象存储(字符串,整数,......)

由于它们是不可变的,因此对用户是透明的。它只是节省了内存。

a[0] is b[0]

可能是真或假。另一方面

a[0] is c[0]

始终为True,因为a is c。 (以及修改a更改c

但由于list类型是可变的,a不能是b(在这种情况下,Python不允许自己优化存储)。那些是独立的对象。修改a无法更改b

注意我的"可以是真的还是假的"备注。请在python 3.4中考虑这一点

>>> b=1234567890
>>> a=[1234567890]
>>> b is a[0]
False

Python没有在ba[0]之间建立链接。长字符串也会发生(我认为这是一个性能问题而连续2次找到一个确切的大数字的概率很低?而1在整个程序中有更好的机会重复)

但是,如果你这样做,你会得到不同的结果:

>>> b=1234567890
>>> a=[b,1,2]
>>> b is a[0]
True

(我不会确定为什么因为它可以根据是否存储为长整数或仅仅是int,值或地址等而有所不同......但是Python肯定有更多关于价值的信息。在这里重复!)

结论是:不要依赖于不可变对象。始终使用==

答案 1 :(得分:0)

int不可变的。这意味着当您重新分配a[0]时,您不会更改1的任何内容。相反,您正在改变a[0]持有的任何内容。你不能改变1的含义 - 你改变了a[0]的含义。

如果另一方面你这样做了:

L = [1,2,3]
a = [L]
b = [L]
a.[0].append(4)

您还会看到b中反映的变化

答案 2 :(得分:0)

Python中的赋值是通过引用 - 它为对象创建一个新的引用或别名,而不是复制对象 - 并且因为事件 int 是Python中的一个对象 - 至少(在我的版本中) - 最多256个),这个规则主要起作用。

以下示例机智函数 id - 显示对象引用 - 说明了点

In [37]: a = range(1, 6)

In [38]: b = range(1, 6)

In [39]: id(1)
Out[39]: 4298160472

In [40]: id(a[0])
Out[40]: 4298160472

In [41]: id(a)
Out[41]: 4376534696

In [42]: id(b)
Out[42]: 4378531744

In [44]: c = a

In [45]: id(c)
Out[45]: 4376534696

然而,这不适用于浮点数 - 这是合乎逻辑的,因为浮点数和整数是无限的

In [49]: a = .1

In [50]: b = .1

In [51]: id(a)
Out[51]: 4298708040

In [52]: id(b)
Out[52]: 4303248152

正如您所看到的,为每个新浮点创建了新对象,尽管值相同