PyTorchの公式チュートリアルであるDeep Learning withPyTorch: A 60 Minute Bitzの日本語訳といくつか補足したものです。
自分はこれまでTensorflowをメインに研究などのコードを作成したのでChainerについてはあまり知識がありません。
PyTorchとは何か
Pythonの科学計算パッケージ。ターゲットとなっているのは以下の二つの層。
1. GPUを使用するためにNumPyからの以降。
2. 柔軟かつ素早い実装が可能な深層学習研究プラットフォーム。
Getting Started
まずはPyTorchで用いられている基本的な概念について。
Tensor
TensorはNumpyのndarrayと似ているものの、GPUで利用されることができ、計算を加速することができる。
例えば、5x3の行列を作成したい場合はtorch.Tensor
を使って以下のように初期化できる。ちなみにtorch.tensor
は実際にはtorch.FloatTensor
のエイリアスになっており、32-bit signed integerなどを初期化したい場合にはtorch.IntTensor
などを用いる。
import torch
x = torch.Tensor(5,3) # 5X3初期化されていないの行列が生成される。
またtorch.rand()
でランダムに初期化された行列を生成することもできる。
x = torch.rand(5,3)
print(x)
Tensorのサイズを確認したい時はsize()
というクラスメソッドでTensorのサイズを表すtorch.Size
が返される。
print(x.size()) # torch.Size([5,3])が出力される
ちなみにこのtorch.Size
はtupleとなっているため、Pythonの通常のtupleと同様の操作が可能。例えば x.size()[0]
とすればTensorの一次元目の大きさを取得できる。
Operations
PyTorchには様々演算記法があり、以下でそれらを紹介する。
和(addition)
まず基本的な+
を用いた和の演算とtorch.add(a,b)
を用いた以下の方法がある。
x = torch.rand(5,3)
y = torch.rand(5,3)
print(x+y)
print(torch.add(x,y)) #どちらでも同様の演算結果を得ることができる
また、torch.add(a,b)
を用いる場合、オプショナルな引数out
を用いて結果を別のtensorに格納することも可能。
result = torch.Tensor(5,3)
torch.add(x,y, out=result)
print(result) # 先ほどのx+yと同様の結果がresultに格納される。
またPyTorchにおいて、Tensorをin-placeに変更する(つまり元のTensorの中身を書き換えてしまう)ような演算には関数名の後に接尾辞(postfix)として_
がつく。
例えば、あるTensorをin-plceに転置するTensor.t_()
メソッドなど。
>>> x = torch.rand(3,5)
>>> x.t_()
0.9643 0.6642 0.7152
0.8060 0.8571 0.8347
0.5978 0.3552 0.2373
0.3823 0.3224 0.9044
0.7525 0.7579 0.0206
[torch.FloatTensor of size 5x3]
>>> x
0.3229 0.8450 0.7299
0.7590 0.0953 0.8313
0.4026 0.4635 0.1336
0.0777 0.3386 0.9635
0.0899 0.3295 0.1540
[torch.FloatTensor of size 5x3]
# 3x5のTensorだったxが5x3に転置されているのが確認できる。
>>> x = torch.rand(3,5)
>>> x.t()
0.3229 0.8450 0.7299
0.7590 0.0953 0.8313
0.4026 0.4635 0.1336
0.0777 0.3386 0.9635
0.0899 0.3295 0.1540
[torch.FloatTensor of size 5x3]
>>> x
0.3229 0.7590 0.4026 0.0777 0.0899
0.8450 0.0953 0.4635 0.3386 0.3295
0.7299 0.8313 0.1336 0.9635 0.1540
[torch.FloatTensor of size 3x5]
# x自体は3x5のまま。
add()
演算についても、in-placeで以下のように書きあらわすことができる。
x = torch.rand(5,3)
y = torch.rand(5,3)
y.add_(x)
print(y)
Tensorの大きさを変更する
Tensorの大きさを変える際にはtensor.view
を用いる。(tensorflowと比べるとちょっと名前がわかりにくいですね)
torch.view()
はin-placeな演算ではないので、元のtensorは変更されない。
x = torch.randn(4,4)
y = x.view(16) # 4x4の行列が16x1のに変形される
z = x.view(-1,8) # -1が含まれる場合、他の次元に合わせて整形される。ここでは一方の次元が8なので16/8=2となる。
Numpy Bridge
NumpyのarrayをTorchのtensorに変換したり、その逆を行うことも可能。
TensorをNumpyのarrayに変換する
>>> a = torch.ones(5) # 要素が全てfloatの1の5x1のベクトルが出力される
1
1
1
1
1
[torch.FloatTensor of size 5]
>>> b = a.numpy() # TensorをNumpy化する
>>> print(b)
[1. 1. 1. 1. 1.]
NumpyのarrayをTorch Tensorに変換する
import numpy as np
a = np.ones(5) # 5x1の要素が全て1のNumpy配列を作成
b = torch.from_numpy(a) # bはサイズが5のdoubleのTTensorになる
np.add(a, 1, out=a)
print(a)
print(b)