Pytorchに段々慣れてきたので、ここまでの段階で最低限押さえておきたいことをまとめておきます。学習には右の本を使っています。
1,Pytorchで使うデータはtensor形式
Pytorchで使うデータはtensor形式です。numpyのデータは、例えばnumpyで作ったx_trainならば、
x_train = torch.tensor(x_train).float( )
とするだけでできます。データは基本的に浮動小数にしますが、多値分類のときのラベルデータは整数にします。
y_train = torch.tensor(y_train).long( )
2,画像データは並べ方を変換。
以前作ったジブリの画像のようなカラー画像は、numpyではこのように並んでいます。
<class 'numpy.ndarray'> (420, 162, 300, 3)
これは事例の数が420,画像縦幅が162,横幅が300,チャンネル(色の種類)が3を意味しています。
pytorchでは個の並べ方を 事例の数、チャンネル、横幅、縦幅の順に並べないとエラーが出て動いてくれません。
データの並べ方の変換は、torchのpermute関数でできます。これを調べるのに半日かかってしまった。
使い方は
x_train_permuted = torch.permute(x_train, (0, 3, 2, 1))
第1引数は変換したいnumpyデータ、第2引数は変換後の並べ方。
この0,3,2,1の意味ですが、これはnumpyのデータだった時の並べ順である
0番目:データ数、1番目:縦幅、2番目:横幅、3番目:チャンネル数
の*番目の数字をタプル形式でPytorch用の場所に入れたものです。
3,GPUを使うときはdeviceを宣言して、データと使用するモデル(予測関数)をdeviceに載せる。
GPUを使うときは、コードの最初の方で、
device = torch.device('cuda:0' if torch.cuda.is_available( ) else 'cpu')
と書いておけば大丈夫です。もしGPUが使えないときは自動的にCPUを使ってくれます。
データと使用するモデル(予測関数)をdeviceに載せるというのは、
先ほどtensor型にしたx_trainならば、
x_train = x_train.to(device)
とすれば完了です。
モデルも同じように
model = model.to(device)
もしデータやモデルの一部を載せ忘れると
cudaとcpuが混在して処理できませんみたいなエラーが出ます。
4,予測関数のパラメータ修正のタイミングを明示的に書いてやる必要がある
kerasの時は損失(loss)関数と最適化関数を定義するだけで、勝手に誤差を求めてパラメータ修正をやってくれました。
pytorchでは「予測関数にx_trainを入れて予測値y_predを求め、y_predと正解値のy_trainを損失関数に入れて、明示的に損失を求める必要があります。そして求めた損失の勾配計算をして、パラメータ修正。」Pytorchではカッコ内の繰り返しを明示的に書く必要があります。
これだけでたったの5行程度のものですので苦にはなりませんが、kerasから乗り換えるとこれはいったい何やっているのかと戸惑うところです。2~3回コードを書いてみるとすぐ慣れます。
5、GPUを使って求めた最終結果はいったんCPUに落とさないとnumpyに変換できない。
作業が終わって予測結果をまとめたデータを作ろうと思っても、データがGPUに載ったままではnumpyに変換できません。
やっと終わったと思ったのにここでエラーが出ると結構がっかりします。
これではPytorchはkerasと比べてやたらと面倒な気がしますが、何でもきっちり書いてあるということは反面分かりやすさ、見やすさということでもあるのかなと感じます。エラーが出た時の修正のしやすさという点でも使いやすいように思えます。
今回のPytorchの学習の仕上げに、事前学習済みモデルをファインチューニングしてジブリ画像の分類をやってみました。その結果はまた近日中にお知らせします。