假设对函数y = 2xx关于列向量x求导
import torch
x = torch.arange(4.0)
x.requires_grad_(True) # 等价于x=torch.arange(4.0,requires_grad=True)
x.grad # 默认值是None
y = 2 * torch.dot(x, x)
y
tensor(28., grad_fn=<MulBackward0>) #28 = 2 * (0+1+4+9)
反向传播计算y关于x每一个分量的梯度
y.backward()
x.grad
tensor([ 0., 4., 8., 12.])
验证梯度的正确性
x.grad == 4 * x
tensor([True, True, True, True])
计算x的另外一个函数
# 在默认情况下,PyTorch会累积梯度,我们需要清除之前的值
x.grad.zero_()
y = x.sum()
y.backward()
x.grad
tensor([1., 1., 1., 1.])
非标量变量的额反向传播
# 对⾮标量调⽤backward需要传⼊⼀个gradient参数,该参数指定微分函数关于self的梯度。
# 在我们的例⼦中,我们只想求偏导数的和,所以传递⼀个1的梯度是合适的
x.grad.zero_()
y = x * x
# 等价于y.backward(torch.ones(len(x)))
y.sum().backward()
x.grad
tensor([0., 2., 4., 6.])
分离计算
x.grad.zero_()
y = x * x
u = y.detach()
z = u * x
z.sum().backward()
x.grad == u
tensor([True, True, True, True])