2017-07-26 66 views
2

在theano中,獲得某個變量w.r.t的梯度非常容易。一個給定的損失:pytorch:如何直接找到漸變w.r.t.損失

loss = f(x, w) 
dl_dw = tt.grad(loss, wrt=w) 

我得到pytorch被冠上了不同的模式,在那裏你會做這樣的事情:

loss = f(x, w) 
loss.backwards() 
dl_dw = w.grad 

的事情是我可能不想通過做一個完整的向後傳播圖 - 只是沿着需要去w的路徑。

我知道你可以用requires_grad=False定義變量,如果你不想通過他們反向傳播的話。但是,你必須決定在變量創建時(並且requires_grad=False屬性附加到變量上,而不是調用漸變的調用,這看起來很奇怪)。

我的問題是是有一些方法來backpropagate需求(即只能沿着計算dl_dw需要,就像在theano路徑backpropagate)?

+1

我認爲這會很複雜。請注意,您只能爲葉變量設置requires_grad。所以,即使你已經處理了圖中的所有變量,你也不能僅僅切換requires_grad = False或者True來只計算你想要的梯度。還要注意,只有葉變量的漸變只能保留(如果你想要中間變量的話,你需要一個鉤子)。如果您對葉變量的漸變感興趣,則可以將其所有requires_grad = False標準設置爲true,然後將其設置爲true,然後在反向傳播之前對其感興趣。 – mexmex

+1

我想你正在尋找[register_backward_hook](http://pytorch.org/docs/master/nn.html#torch.nn.Module.register_backward_hook)功能。你可以直接用它修改漸變。 – Cedias

回答

1

事實證明,這真的很容易。只需使用torch.autograd.grad

例子:

import torch 
import numpy as np 
from torch.autograd import grad 

x = torch.autograd.Variable(torch.from_numpy(np.random.randn(5, 4))) 
w = torch.autograd.Variable(torch.from_numpy(np.random.randn(4, 3)), requires_grad=True) 
y = torch.autograd.Variable(torch.from_numpy(np.random.randn(5, 3))) 
loss = ((x.mm(w) - y)**2).sum() 
(d_loss_d_w,) = grad(loss, w) 

assert np.allclose(d_loss_d_w.data.numpy(), (x.transpose(0, 1).mm(x.mm(w)-y)*2).data.numpy()) 

感謝JerryLin回答問題here