淺析深拷貝與淺拷貝

01 深拷貝與淺拷貝

1. 定義解釋

簡單理解, 深拷貝和淺拷貝就是拷貝內容的層次深度不一樣。深拷貝所有都是新的(遞歸),淺拷貝只有第一層是新的。python

指向

a = [11, 22] 指在內存中開闢一個空間,存儲[11, 22]這個列表,a 指向這個空間的內存地址。
b = a , 表示b 也指向這個內存地址,沒有開闢新的內存空間。
id(a) = id(b)app

另外: a == b (True) 內容相同, a is b (True) 內存地址相同
code

淺拷貝

淺拷貝只是單純地拷貝要拷貝的東西的指向,可是不拷貝指向的內存地址中的內容。(拷貝C的快捷方式)
對象

import copy
a = [11, 22]
b = [33, 44]
c = [a, b]
e = copy.copy(c)
id(e) = id(c)

id(e)
Out[41]: 2447913914184
id(c)
Out[42]: 2447914220744
id(e[0])
Out[43]: 2447913762952
id(c[0])
Out[44]: 2447913762952

# 在c中新增一個數值,e不會改變
c.append(55)
c
Out[47]: [[11, 22], [33, 44], 55]
e
Out[48]: [[11, 22], [33, 44]]

# 可是在a中新增一個數值,則e也會改變
a.append(66)
c
Out[50]: [[11, 22, 66], [33, 44], 55]
e
Out[51]: [[11, 22, 66], [33, 44]]

代表, 當e = copy.copy(c) 淺copy 時, 只copy了c 的指向,並無生成新的a, bblog

深拷貝

f = copy.deepcopy(c) ,生成了存儲內容跟a, b 同樣的新的內容空間遞歸

f = copy.deepcopy(c)
id(f[0]) == id(c[0])
Out[60]: False

2. 特殊狀況

當拷貝的對象是元組類型時

a = (11, 22)
b = (33, 44)
a = (11, 22)
b = a
c = copy.copy(a)
d = copy.deepcopy(a)
id(b)
Out[67]: 2447914673928
id(c)
Out[68]: 2447914673928
id(d)
Out[69]: 2447914673928

若是copy.copy拷貝的是元組,那麼它不會進行淺拷貝,僅僅是指向。
緣由: 由於元組是不可變類型,那麼意味着數據必定不能修改,所以copy.copy的時候會自動判斷,是元組就指向內存

a = [11, 22]
b = [33, 44]
c = (a, b)
d = copy.copy(c)
e = copy.deepcopy(c)
id(c)
Out[75]: 2447914777800
id(d)
Out[76]: 2447914777800
id(e)
Out[77]: 2447914770824

若是用copy.copy 或者copy.deepcopy對一個所有都是不可變類型的數據進行拷貝,那麼他們的結果相同,都是引用指向。
若是拷貝的是一個不可變類型的數據,即便元組是最頂層,那麼deepcopy依然是深拷貝,而copy.copy仍是指向。class

相關文章
相關標籤/搜索