1.激活函數
1 #激活函數 2 z1=torch.linspace(-100,100,10) 3 print(z1) #tensor([-100.0000, -77.7778, -55.5556, -33.3333, -11.1111, 11.1111, 33.3333, 55.5556, 77.7778, 100.0000]) 4 print(torch.sigmoid(z1)) #tensor([0.0000e+00, 1.6655e-34, 7.4564e-25, 3.3382e-15, 1.4945e-05, 9.9999e-01, 1.0000e+00, 1.0000e+00, 1.0000e+00, 1.0000e+00]) 5 6 z2=torch.linspace(-1,1,10) 7 print(torch.tanh(z2)) #tensor([-0.7616, -0.6514, -0.5047, -0.3215, -0.1107, 0.1107, 0.3215, 0.5047, 0.6514, 0.7616]) 8 9 print(torch.relu(z2)) #tensor([0.0000, 0.0000, 0.0000, 0.0000, 0.0000, 0.1111, 0.3333, 0.5556, 0.7778, 1.0000])
2.loss及其梯度
2.1均方差(MSE)
均方損失函數torch.nn.mse_loss(pred, target)
1 import torch 2 from torch.nn import functional as F 3 4 #y=x*w(b取0) 5 x=torch.ones(1) 6 w=torch.full([1],2) 7 8 #計算均方差 9 #法一 10 mse1=torch.norm(torch.ones(1)-x*w, 2)**2 11 print(mse1) #tensor(1.) 12 #法二 13 mse2=F.mse_loss(torch.ones(1), x*w) 14 print(mse2) #tensor(1.)
2.2梯度計算
torch.autograd.grad(loss, [w1, w2,...])
-
第一個參數是損失函數,第二個參數是該損失函數要求梯度的參數列表
-
返回結果grad_val是梯度列表,列表記錄了每一個Tensor的grade信息
$[\frac{\alpha Loss}{\alpha w1}, \frac{\alpha Loss}{\alpha w2},...]$
1 #對w求導,需要先指明w需要梯度信息 2 w.requires_grad_() 3 print(w) #tensor([2.], requires_grad=True) 4 mse=F.mse_loss(torch.ones(1), x*w) 5 print(torch.autograd.grad(mse, [w])) #(tensor([2.]),)
loss.backward()
圖的反向傳播,自動求出該圖上所有的需要計算梯度的參數相對於這個MSE的梯度,梯度信息附加到每個Tensor的成員變量grad中,不會額外返回。w1.grad,w2.grad...
1 w.requires_grad_() 2 print(w) #tensor([2.], requires_grad=True) 3 mse=F.mse_loss(torch.ones(1), x*w) 4 5 mse.backward() 6 print(w.grad) #tensor([2.])
Tip:這個方法會將之前的梯度信息覆蓋掉,所以多次調用這個loss對象的.backward()方法時會報錯,如果要再次調用以生成新的梯度信息,要給它一個參數.backward(retain_graph=True)。
3.softmax
可以用於將多個輸出值轉換成多個概率值,使每個值都符合概率的定義,范圍在[0, 1],且概率相加和為1,非常適合多分類問題。
1 import torch 2 from torch.nn import functional as F 3 4 a=torch.rand(3) 5 a.requires_grad_() 6 print(a) #tensor([0.4580, 0.6305, 0.0915], requires_grad=True) 7 8 p=F.softmax(a, dim=0) 9 print(p) #tensor([0.3471, 0.4124, 0.2406], grad_fn=<SoftmaxBackward>) 相加為1
1 print(torch.autograd.grad(p[0], [a], retain_graph=True)) #(tensor([ 0.2266, -0.1431, -0.0835]),) 2 print(torch.autograd.grad(p[1], [a], retain_graph=True)) #(tensor([-0.1431, 0.2423, -0.0992]),) 3 print(torch.autograd.grad(p[2], [a])) #(tensor([-0.0835, -0.0992, 0.1827]),)
上面的第一行相當於:
1 p[0].backward(retain_graph=True) 2 print(a.grad)
Tip:
- 計算導數時,loss只能是一個值,不能多個分量,所以分別對p[0],p[1],p[2]對應的loss求導
- loss可以對多個參數求偏導,eg.p0對a0,a1,a2求偏導
- i==j時,偏導為正,i!=j時偏導為負