Autograd:自動求導機制
Pytorch的核心是autograd包。autograd包爲張量上的所有操作提供了自動求導,他是一個運行時定義的框架,意味着反向傳播是根據代碼來確定如何運行,並且每次迭代可以不同
張量(Tensor)
torch.Tensor這個包是核心類,如果設置.requires_grad爲True,那麼將會追蹤所有對於該張量的操作。完成計算後調用.backward,自動計算所有梯度,這個張量的所有地圖會自動更新到.grad屬性
要阻止張量跟蹤歷史記錄,可以調用.detach方法將其與計算曆史記錄分離,並禁止跟蹤其將來的計算記錄
爲防止跟蹤記錄歷史(和使用內存),可以將代碼包裝在with torch.no_grad():中。
import torch
x = torch.ones(2, 2, requires_grad=True)
x
tensor([[1., 1.],
[1., 1.]], requires_grad=True)
# 對張量進行操作
y = x + 2
y
tensor([[3., 3.],
[3., 3.]], grad_fn=<AddBackward0>)
# grad_fn已經自動生成
print(y.grad_fn)
<AddBackward0 object at 0x000001C9019DDAC8>
# 對y進行操作
z = y * y * 3
out = z.mean()
print(z, out)
tensor([[27., 27.],
[27., 27.]], grad_fn=<MulBackward0>) tensor(27., grad_fn=<MeanBackward0>)
# .requires_grad() 可以改變現有張量的requires_grad屬性。默認爲False
a = torch.randn(2, 2)
a = ((a * 3) / (a - 1))
print(a.requires_grad)
a.requires_grad_(True)
print(a.requires_grad)
b = (a * a).sum()
print(b.grad_fn)
False
True
<SumBackward0 object at 0x000001C9019ECA08>
梯度
反向傳播 因爲out是一個純量(scalar), out.backward()等於out.backward(torch.tensor(1))
out.backward()
print(x.grad)
tensor([[4.5000, 4.5000],
[4.5000, 4.5000]])
x = torch.randn(3, requires_grad=True)
y = x * 2
while y.data.norm() < 100:
y = y * 2
print(y)
tensor([-23.7332, 42.4670, -88.6353], grad_fn=<MulBackward0>)
gradients = torch.tensor([0.1, 1.0, 0.001], dtype=torch.float)
y.backward(gradients)
print(x.grad)
tensor([ 12.8000, 128.0000, 0.1280])
print(x.requires_grad)
print((x**2).requires_grad)
with torch.no_grad():
print((x**2).requires_grad)
True
True
False