パドック画像から競走馬の距離適性を推測する学習をしてみたけど性能が全然よくない…!
ヒィィ (ノ゚ρ゚)ノ
う〜ん、やっぱりデータのサンプル数が少なすぎるのかな・・
ということでchainerのCIFAR-10のサンプルコードを使って学習データ数と認識精度の関係をちょっと調べてみました。
実験条件
- epoch数: 100
- 学習データ数: 1000, 3000, 5000, 10000, 50000
結果
やっぱり、機械学習の世界では 数は性能なり なんですね。。
Udacityのディープラーニング講座の中で使うTensorFlowのバージョンが1.0となっていてCUDA7.5だと動かない… (>_<)
ということで自宅PCのCUDAを7.5から8.0にアップグレードしました。
今まで自分にとって開発環境のアップグレードは鬼門で 今まで動いていたものがいろいろ動かなくなって
ああ、やらんかったらよかった…
ということが多々あったのですが今回はあまりにもスムーズでうれしかったのでメモを残します。(´ー`)
NVIDIAのダウンロードサイトからCUDAをダウンロードしてきます。
自分のPCにあったものを選択します。Ubuntu14.04用は https://developer.nvidia.com/compute/cuda/8.0/Prod2/local_installers/cuda_8.0.61_375.26_linux-run
chmod a+x cuda_8.0.61_375.26_linux-run sudo service lightdm stop # Stop X-Server sudo bash ./cuda_8.0.61_375.26_linux.run --silent --no-opengl-libs --toolkit
1分ぐらい待つと何のメッセージ出力がなく終了します。
えっ?( ´・д・)
と思うぐらい拍子抜けです。
続いて以下のコマンドでCUDAがインストールされていることを確認します。
nvidia-smi # check GPU is available nvcc -V # cuda version should be 8.0
続いてcuDNNをインストール。こちらもNVIDIAのサイトからダウンロードしてきます。 cuDNNはNVIDIAのユーザー登録が必要です。
ユーザー登録面倒な方はこちらからダウンロードしてください http://momonoki.blob.core.windows.net/data/cudnn/cudnn-8.0-linux-x64-v5.1.tgz
tar xvfz cudnn-8.0-linux-x64-v5.1.tgz cat /usr/local/cuda/version.txt # /usr/local/cudaがcuda-8.0へのリンクになっていることを確認 sudo cp cuda/include/cudnn.h /usr/local/cuda/include sudo cp cuda/lib64/* /usr/local/cuda/lib64
そのままだとCUDAのバージョン不一致で動かないので一度アンインストールしてからインストールします。
# reinstall chainer pip uninstall chainer pip install chainer # reinstall TensorFlow pip uninstall tensorflow pip install tensorflow-gpu
再インストールしたらMNISTのサンプル等でGPUありで動くかを確認します。
以上です。
今日は誤差逆伝搬法(Backpropagation)について書いてみます。
Karpathy先生のCS231nの講義が秀逸すぎるのでそれを見れば十分です! (◍•ᴗ•◍)
これではあんまりなので特に覚えておきたいポイントをまとめてみようと思います。。
微分の連鎖律(チェインルール)です。
RNNのhiddenノードも出力層からの誤差と次のRNNセルからの誤差が加算されます。(hは次のRNNセルへの入力でもあるため)
computational graph | network layer graph |
---|---|
入力がベクトルの場合も同じです。ただ、行列(W)の次元を考慮する必要があります。 掛け算するために転置(T)をしたり、掛ける順番を考慮しないと怒られます..。
個人的には computational グラフで考えると誤差の伝搬が計算しやすいです。
このようにバッチ単位でまとめて行列計算したいときは W は (insize, outsize) となります。 また、WX ではなく D = XW と掛け算します。
今回はここまでです。 マウスで文字を書くのつらい.. (ノ゚ο゚)ノ
機械学習が何をやっているか、、一言で言えば 誤差を最小化するを見つける ということになります。
関数の最小値を求めると言えば高校の数学でも微分を使って最小値を求めていましたが、機械学習の最小化問題は枠組みが少し違っています。
高校の数学 | 機械学習 |
---|---|
L'(w) = 0 となる w を 直接的に計算する | あるwが与えられたとき、L'(w) が 0 に近づく wを動かす向き を見つける |
のとき となるのは のとき このとき、最小値 |
右図のように勾配(gradient)を計算して変数を更新していきます。 実際には誤差関数はいくつかの変数からなる関数なので偏微分(partial derivative)で勾配を求めます。
いずれにせよ、微分は知っておく必要があります。。┗(`・∀・´●)
実際にはいくつもの演算が組み合わさった結果を微分することになるので目的の変数の勾配を計算するにはチェインルール(連鎖律)を知っておく必要があります。
マストです。。 (゜ロ゜)
、 であるとき
とおくと
個人的にはPFNの岡野原さんのスライドがイメージを掴みやすかったです。
とりあえず、以下を知っていれば大抵は何とかなるはず・・・
関数 | 導関数 |
---|---|
スクラッチで実装すると自信がつく気がします。。 (o・ω・o)
前回でパドック画像を収集しました。今回は各パドック画像のラベリングを行い学習データを作ります。
これまたnetkeibaにお世話になります。m(._.*)m
netkeibaの各馬のデータには 適性レビュー というデータがあります。 この適性レビューの 距離適性のパラメータ を利用します。
例えば、オルフェーヴルの距離適性のデータは以下のようになっています。 距離適性が 短い/長い のバーの長さの割合で表現されています。
htmlコードを見てみます。
“短い” と “長い” のバーの長さが widthの数値で取得できそうです。(^○^)
距離適性は次式
で計算します。
この値が 0.0 に近ければ 短距離馬 で 1.0 に近ければ 長距離馬 になります。
馬名を入力として 先ほどの距離適性の値を取得します。 使ったコードはこちらにあります。
2525頭分の計算結果は https://github.com/tanakatsu/netkeiba_distance_aptitude/blob/master/sample.sorted_score.txt
になります。
私の肌感覚でざっくり分類すると、
category | score |
---|---|
長距離 | 0.6- |
中距離 | 0.4-0.59 |
マイラー | 0.2-0.39 |
短距離 | -0.19 |
っていうところでしょうか。
ただ、明確に線引きすることは難しそうなので長距離と短距離の分類(Classification)とかではなく回帰(Regression)として扱うのがよさそうです。
次はいよいよ学習です。 ((((o゚▽゚)o)))
UdacityのDeepLearning基礎コース、Week3以降は週5-6時間程度でレッスンコンテンツは一通りはこなせています。 ただ、後でしっかり復習しないと身につかない感じはあります。。 そりゃそうですよね、、世の中そんなに甘くない。(;^_^A
今日は行列の積についてメモを残します。
学校の授業で習ったいわゆる行列の掛け算はdot演算と呼ばれるものになります。
elementwise演算は 単純に要素同士を掛け算するだけです。
numpyにはブロードキャストという仕組みがあるので列数と行数が一致していなくても演算可能になっています。ここが混乱しどころです。これは numpyが演算するときにサイズを変換してくれるためです。
ブロードキャストできるかどうか? Broadcasting — NumPy v1.12 Manual
*演算 | dot演算 | |
---|---|---|
(m, 1) x (1, n) | ok | ok |
(m, 1) x (n, 1) | NG | NG |
(m, 1) x (n,) | ok | NG |
(n,) x (m, 1) | ok | NG |
okのパターンでは (m, n)の行列が出力されます。
ディープラーニングで出てくる計算の中で2種類の掛け算をどう使い分けるのか、、、
ざっくりまとめてみました。
*演算 | dot演算 |
---|---|
1つのノード内での計算 (シグモイドの微分計算etc) |
複数ノード間の計算 (重みWとベクトルとの計算) |
例1: シグモイドの微分 例2: 入力誤差の伝搬 |
例1: 順伝搬 例2: 入力誤差の計算 例3: 誤差からを計算 |
入力の次元数と出力の次元数が同じときは *演算 と考えていいです。
dot演算の例3では 入力が1次元のベクトルの場合に、*演算としても計算可能ですが2次元以上の場合に計算できないので dot演算として考えるのが無難でしょう。
次の例のようにCNN (Convolutional Neural Network) で何か面白い分類をやってみたい
MNISTやCifar10と言ったような練習用のありきたりのデータではなく何かcoolな題材はないかな〜と考えていたところ、、
馬体から短距離馬と長距離馬を見分けられたら面白いのではないか?(また、競馬かよ)
そう、短距離馬と長距離馬は首筋の長さ、太さで特徴が違うのです。
もしかしたらディープラーニングで見分けられるかも〜?! ¨キ(o゚Д゚o)¨キ
ということで、パドック画像を探してみます。パドック画像だけを取りまとめているリソースがなかなか見つかりませんでしたが、、、
ありました! 競馬道のサイトの競馬ブックコーナーです。ヽ( ´¬`)ノ
早速、クローラを実装して画像を収集させていただきました。ソースコードはこちらにあります。
2001年より前はフォーマットが違っていて以下のように写真の中に文字も含まれてしまうので2002年以降の写真を収集しました。
http://www.keibado.ne.jp/keibabook/010109/photop.html
2017年1/23時点で のべ頭数 8707頭、ユニーク頭数としては 2528頭分の画像を収集できました。
収集した画像はこちらからダウンロードできます。
http://www.keibado.ne.jp/keibabook/170109/images/pp01.jpg
の画像URLの場合、170109_pp01.jpg
として保存しています今回はここまでです。