2016年7月18日月曜日

Fully Convolutional Networks 〜 Chainerによる実装 再考2 〜


はじめに


 先のページで、fcn32sを Chainer を使って実装した。今回は、fcn32sの訓練済みモデルを使って、fcn16sの学習を行う。

学習曲線


 最初に学習曲線を示す。

Accuracy
Loss
今回はEpoch60回で打ち切った(かろうじて収束していないように見えるが課金量の関係である)。テスト画像の正解率は94%程度となり前回の92%より向上した。このあとfcn8sを行うことになる。

計算機環境


 前回と同じく、Amazon EC2 にある g2.2xlarge を利用した。GPU を搭載したインスタンスである。今回もミニバッチ処理ができないので1枚ずつ学習する。

データセット


 訓練画像、テスト画像ともに前回と全く同じである。

ネットワークの構造


 ネットワークの構造は以下の通りである。
前回と同じである。上記の表では224$\times$224の正方形画像を想定してその1辺の長さだけをinputに記してあるが、縦横の長さは任意で構わない。表の各項目の意味は以下の通りである。
  1. name: 層の名前
  2. input: 入力featureマップの1辺のサイズ
  3. in_channels: 入力featureマップ数
  4. out_channels: 出力featureマップ数
  5. ksize: カーネルのサイズ
  6. stride: ストライドのサイズ
  7. pad: paddingのサイズ
  8. output: 出力featureマップの1辺のサイズ
今回はfcn16sを実装するのでpool4、pool5 の出力に接続する層(score-pool4、score-pool5)が必要である。これを通ったあとの出力データ名をそれぞれp4、p5とする。p4とp5のfeatureマップの数はクラスの数に等しくなる。
この表も、正方形画像を想定してその1辺の長さをinputに記してあるが縦横任意で構わない。出力p5はbilinear補間で2倍され、p4に加算される。そのあと、元画像と同じサイズに拡大され、ラベル画像と比較される。


ネットワークの実装


 上記の構造をそのままChainerで記述する。

-- myfcn_16s_with_any_size.py -- 物体の境界線には-1を配置し、softmax_cross_entropyの計算時に境界の寄与を無視するようにした。また、関数F.accuracyの引数 ignore_labelを使えば境界線上の画素を除いてaccuracyを計算することができる。112行目から113行目にかけて記述した関数でp5を2倍に拡大し、116行目でp4に加算している。122行目から123行目にかけて記述した関数で加算結果を16倍し、126行目でラベル画像との間のクロスエントロピーを計算している。

訓練


 訓練時のスクリプトは以下の通りである。

-- train_16s.py -- 関数 copy_model は前回と同じである。 train_16s.pyでしていることは、
  1. オブジェクトmini_batch_loader_with_any_sizeを作る。
  2. fcn32sで学習したモデルを読み込む。
  3. MyFcn16sWithAnySize.pyで定義されたネットワークのオブジェクトを作る。
  4. 学習済みモデルのパラメータをこれにコピーする。
  5. 最適化アルゴリズムとして MomentumSGD を選択する。
  6. あとは、通常の訓練過程である。
mini_batch_loader_with_any_size.pyは前回と同じである。

結果画像


 以下にテスト画像に適用した結果を示す。左の列はfcn32sの結果、中央の列はfcn16sの結果、右の列はGround Truthである。下に記した数値はaccuracyである。ここでaccuracyとは、1枚の画像の中で何%の画素が正解したかを計算したものである(境界線上の画素は除く)。

一番最後の画像以外は、精度は向上している。

ダウンロード


 ここの、タグが2016-07-17のものです。

1 件のコメント: