pytorch提供了clone、detach、copy_和new_tensor等多種張量的復制操作,尤其前兩者在深度學習的網絡架構中經常被使用,本文旨在對比這些操作的差別。
1. clone
返回一個和源張量同shape、dtype和device的張量,與源張量不共享數據內存,但提供梯度的回溯。
clone
后的返回值是個中間variable,因此支持梯度的回溯。因此,clone
操作在一定程度上可以視為是一個identity-mapping函數。
clone
作為一個中間variable,會將梯度傳給源張量進行疊加。
但若源張量的require_grad=False
,而clone
后的張量require_grad=True
,顯然此時不存在張量回溯現象,clone
后的張量可以求導。
綜上論述,clone
操作在不共享數據內存的同時支持梯度回溯,所以常用在神經網絡中某個單元需要重復使用的場景下。
2. detach
detach
的機制則與clone
完全不同,即返回一個和源張量同shape
、dtype
和device
的張量,與源張量共享數據內存,但不提供梯度計算,即requires_grad=False
,因此脫離計算圖。
detach
后的張量,即使重新定義requires_grad=True
,也與源張量的梯度沒有關系。
綜上論述,detach
操作在共享數據內存的脫離計算圖,所以常用在神經網絡中僅要利用張量數值,而不需要追蹤導數的場景下。
3. clone和detach聯合使用
clone提供了非數據共享的梯度追溯功能,而detach又“舍棄”了梯度功能,因此clone和detach聯合使用意味着着只做簡單的數據復制,既不數據共享,也不對梯度共享,從此兩個張量無關聯。
置於是先clone還是先detach,其返回值一樣,一般采用tensor.clone().detach()。
4. new_tensor
new_tensor
可以將源張量中的數據復制到目標張量(數據不共享),同時提供了更細致的device
、dtype
和requires_grad
屬性控制:
其默認參數下的操作等同於.clone().detach()
,而requires_grad=True
時的效果相當於.clone().detach()requires_grad_(True)
。上面兩種情況都推薦使用后者。
5. copy_
copy_
同樣將源張量中的數據復制到目標張量(數據不共享),其device
、dtype
和requires_grad
一般都保留目標張量的設定,僅僅進行數據復制,同時其支持broadcast操作。
具體試驗參考:
【Pytorch】對比clone、detach以及copy_等張量復制操作