python 中的拷貝、淺拷貝與深拷貝

0.序列指什麼?

序列類型是指容器內的元素從0開始的索引順序訪問,一次可以訪問一個或者多個元素,包括字符串(string)、元組(tuple)、列表(list):
The difference between tuple and list:
Tuple would not be changed, but list would.
>>> a = (1,2,3)
>>> b = [1,2,3]
>>> b.append(4)
>>> a.append(4)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'tuple' object has no attribute 'append'
1.什麼是拷貝?
Copy操作意味着兩個在內存中不同的對象,所以對應的id也是不一樣的。
>>> ls1 = [1,2,3]
>>> ls2 = ls1[:]
>>> id(ls1),id(ls2)
(140439195044104, 140439195058760)
>>> tp1 = (1,2,3)
>>> tp2 = ls1[:]
>>> id(tp1),id(tp2)
(140439194958816, 140439194958816)
爲什麼tuple的id沒有變化而list的tuple發生了變化了呢?這個是由於Python解釋器的實現導致的,由於tuple是immutable的,所以說沒有必要在內存裏維護多個一樣字面意義的tuple,因此Python對於Tuple的Copy操作,實際上是增加了一個Reference Count而已,並沒有做真正的Copy,所以ID的返回值是一樣的。

這是淺拷貝還是深拷貝?
一般以下所得到的都是淺拷貝:

2.什麼是淺拷貝?
淺拷貝是指當序列中包含容器時,拷貝後新序列的容器只是原序列容器的引用

>>> a = (1,3,5,[2,4])
>>> b = a[:]
>>> b[3].append(6)
>>> a,b
((1, 3, 5, [2, 4, 6]), (1, 3, 5, [2, 4, 6]))

3.什麼是深拷貝?
深拷貝是指拷貝後序列中的容器也拷貝過去,而不存在引用關係。

>>> c = copy.deepcopy(a)
>>> c[3].append(8)
>>> a,c
((1, 3, 5, [2, 4, 6]), (1, 3, 5, [2, 4, 6, 8]))

4.總結:
考察是不是淺拷貝的方法是兩者的容器是否指向同一個地址。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章