機械学習・自然言語処理の勉強メモ

学んだことのメモやまとめ

PyTorch入門①:Tensors~Autograd

はじめに



流行りに乗っかってPyTorchを勉強する。
最近、PyTorchで実装する論文が急増しているらしく、とりあえずソースコードが読めるようになりたい。

Tensors



Numpyのndarrays(多次元配列)のようなもの。
GPUの高速計算のために使われるオブジェクトとのこと。

以降のサンプルはチュートリアルのもの。
What is PyTorch? — PyTorch Tutorials 0.3.0.post4 documentation

作り方

1)初期化を行わず作成

from __future__ import print_function
import torch
x = torch.Tensor(5, 3)
print(x)

2.3942e-37 0.0000e+00 -2.6457e+08
4.5848e-41 -3.8321e+08 4.5848e-41
1.0433e-37 0.0000e+00 1.0433e-37
0.0000e+00 -7.6205e+15 4.5848e-41
-7.5137e+15 4.5848e-41 -2.2547e+05
[torch.FloatTensor of size 5x3]

2)ランダム値で初期化

x = torch.rand(5, 3)
print(x)

0.2182 0.7903 0.7750
0.4161 0.2828 0.3396
0.9726 0.6395 0.3299
0.3787 0.3909 0.6220
0.5164 0.6238 0.5192
[torch.FloatTensor of size 5x3]

サイズの取得
print(x.size())  # torch.Size([5, 3])
足し算
y = torch.rand(5, 3)
print(x + y)

このような書き方でも良い。

result = torch.Tensor(5, 3)
torch.add(x, y, out=result)

# adds x to y
y.add_(x)
リサイズ

reshapeではないので注意が必要。

x = torch.randn(4, 4)
y = x.view(16)
z = x.view(-1, 8)  # the size -1 is inferred from other dimensions
print(x.size())  # torch.Size([4, 4]) 
print(y.size())  # torch.Size([16]) 
print(z.size())  # torch.Size([2, 8])
Numpyとの橋渡し

1)Torch Tensor → NumPy Array

a = torch.ones(5)
b = a.numpy()
print(b)  # [ 1.  1.  1.  1.  1.]

a.add_(1)
print(b)  # [ 2.  2.  2.  2.  2.]  

*Tensorで値を変えるとNumpyのArrayの値も変わる。

2)NumPy Array → Torch Tensor

import numpy as np
a = np.ones(5)
b = torch.from_numpy(a)
np.add(a, 1, out=a)

*Numpyで値を変えるとのTensorの値も変わる。

CUDA Tensors

GPU上でTensorを操作する場合、

if torch.cuda.is_available():
    x = x.cuda()
    y = y.cuda()
    x + y

Variable



Tensorをラップしたクラス。
このようなクラス構造。
f:id:kento1109:20180213152129p:plain

x = Variable(torch.ones(2, 2), requires_grad=True)
print(x)

Variable containing:
1 1
1 1
[torch.FloatTensor of size 2x2]

Autograd



自動微分機能のこと。
Autograd: automatic differentiation — PyTorch Tutorials 0.3.0.post4 documentation

Theanoよりシンプル。

import torch
from torch.autograd import Variable

x = Variable(torch.Tensor([2]), requires_grad = True)
w = Variable(torch.Tensor([1]), requires_grad = True)
y = w*x**2
y.backward()
print(x.grad)
print(w.grad)   

Variable containing:
4
[torch.FloatTensor of size 1]

Variable containing:
1
[torch.FloatTensor of size 1]