看《流畅的Python》8.3节默认做浅拷贝,自己动手实践。
书中提到的网站http://pythontutor.com是一个可视化编程的网站。
csdn不支持图片粘贴,我也是服了,图片全没了。。。
一、浅拷贝
在http://pythontutor.com/visualize.html#mode=edit下输入:
import copy
l1 = [3, [66,55,44], (7,8,9)]
l2 = list(l1) # shallow copy
# l3 = copy.copy(l1) # same as l2
# l4 = l1[:] # same as l2
l1.append(100) # append only after l1
l1[1].remove(55)
print(l1)
print(l2)
l2[1]+=[33,22]
l2[2]+=(10,11) # this will create a new tuple
print(l1)
print(l2)
点击Visualize Execution,在下一个页面点击Forward,程序一行行执行。
1.执行完浅拷贝:
程序运行到第8行之前,l1,l2的状态如右图:
l2是l1的浅拷贝,l2是一个新list,但list里的list [66,55,44]、tuple (7,8,9)和l1 还是共享的。
2.执行到13行之前
第8行的append,只影响了l1, l2没有影响。
第9行的remove,操作的是l1、l2共享的的list
运行结果如下:
3.程序最终结果:
第13行,操作的是共享的list
第14行,对不可变tuple来说,+=操作会生成一个新tuple,相当于tuple_new = tuple_ole + (10, 11),让后重新绑定到l2[2]
二、深拷贝
修改代码,使用copy.deepcopy
import copy
l1 = [3, [66,55,44], (7,8,9)]
l2 = copy.deepcopy(l1) # deep copy
l1.append(100)
l1[1].remove(55)
print(l1)
print(l2)
l2[1]+=[33,22]
l2[2]+=(10,11) # this will create a new tuple
print(l1)
print(l2)
1.执行到第6行之前
l2会生成一个新list,不在和l1共享
2.执行到11行之前
第6、7行,由于是深拷贝,只影响l1
3.程序最终状态
11行,在l2[1]后append
12行,新生成一个tuple,绑定到l2[2]上