python中copy和deepcopy
python中的copy分为浅copy和深copy,即copy和deepcoy
对于浅copy来说相当于换了一层皮,可以理解为windows给一个软件加了一个额外的快捷方式。
对于深copy来说相当于脱胎换骨头,可以理解为windows重新安装了一套一模一样的软件。
下面我们用代码验证一下
用浅copy
import copy
a = [100, 2, 3, [4]]
b = copy.copy(a)
print(a == b)
print(a is b)
print(a[0] == b[0])
print(a[0] is b[0])
print(a[3] == b[3])
print(a[3] is b[3])
a[0] = -100
print(a[0] == b[0])
print(a[0] is b[0])
a[3].append(5)
print(a[3] == b[3])
print(a[3] is b[3])
打印结果如下
True
False
True
True
True
True
False
False
True
True
打印结果很有意思,我们先不分析,看下深copy的结果
import copy
a = [100, 2, 3, [4]]
b = copy.deepcopy(a)
print(a == b)
print(a is b)
print(a[0] == b[0])
print(a[0] is b[0])
print(a[3] == b[3])
print(a[3] is b[3])
#注1
a[0] = -100
print(a[0] == b[0])
print(a[0] is b[0])
a[3].append(5)
print(a[3] == b[3])
print(a[3] is b[3])
打印结果
True
False
True
True
True
False
False
False
False
False
对这样的打印结果是否感到意外
对于浅copy的结果我们可能估计的是
True
False
True
True
True
True
True
True
True
True
对于深copy的结果我们可能预估的是
True
False
True
False
True
False
False
False
False
False
我们提出几个问题
- 浅copy不是只换了一层皮吗?那么为什么对a[0]的修改不会对b[0]产生影响(由注1可知)
- 深copy不是脱胎换骨吗?那为什么a[0] is b[0] 的结果是true呢
其实这里是python对数字做了缓存,如果内存中已经由100这个值了,在生命新的变量值为100时,python将不会开辟新的内存,而直接将新的变量指向100这个值的地址。加入新的变量值需要变化为-100时,由于原有地址还有别的变量在引用,所以只能开辟新的地址,并让变量指向新的地址。
所以出现上面的结果也就不奇怪了。