自動微分
ニューラルネットワーク学習で最も使われるのはバックプロゲーションです。
この章ではパラメータに対する損失関数と勾配に基づいてパラメータが調整されることを見ていきましょう。
勾配を計算する上で PyTorchにはtorrch.autograrというすでに関数が揃っております。
以下はxを入力し、パラメータw(重さ),b(バイアス)を処理内で加える。
yは正解値
zはx,w,bより作られた予測値
lossはbinary_cross_entropy_with_logitsで正解値とどの程度ズレがあるかを確認する
requires_grad=Trueは後で逆伝潘を行うから計算の途中式を記憶しておいてという意味
→学習済みの場合で回答だけが欲しい時は逆伝潘を行う必要がない(時間を短縮したい)ので、Falseに設定する等
import torch
x = torch.ones(5) # input tensor
y = torch.zeros(3) # expected output
w = torch.randn(5, 3, requires_grad=True)
b = torch.randn(3, requires_grad=True)
z = torch.matmul(x, w)+b
loss = torch.nn.functional.binary_cross_entropy_with_logits(z, y)
どのような値が出力されたかを確認する関数は以下になる。
print(f"Gradient function for z = {z.grad_fn}")
print(f"Gradient function for loss = {loss.grad_fn}")
Gradient function for z = <AddBackward0 object at 0x102cea8f0>
Gradient function for loss = <BinaryCrossEntropyWithLogitsBackward0 object at 0x102cea8f0>
勾配の計算
ニューラルネットワークの重みを最適化するには損失関数のパラメータに関するどう関数を計算する必要があります。
そのためにbackward()を使用し計算式を逆走します。
計算された値は.grad()に格納され各々をw.grad(),b.grad()に渡す
loss.backward()
print(w.grad)
print(b.grad)
tensor([[0.1518, 0.0519, 0.0011],
[0.1518, 0.0519, 0.0011],
[0.1518, 0.0519, 0.0011],
[0.1518, 0.0519, 0.0011],
[0.1518, 0.0519, 0.0011]])
tensor([0.1518, 0.0519, 0.0011])
また学習が終了し入力データに対する出力だけを確認したい場合はgradをする必要がなくなります。
その場合はtorch.no_grad()を行えば対応できます。
z = torch.matmul(x, w)+b
print(z.requires_grad)
with torch.no_grad():
z = torch.matmul(x, w)+b
print(z.requires_grad)
True
False
