U-net semantic segmentation セグメンテーション AI 機械学習

AI

U-netの使い方と実装方法について【PytorchによるSemantic segmentation】

2021年11月14日

こんにちは。産婦人科医のとみー(Twitter:@obgyntommy)といいます。

 

私は普段は画像系の機械学習の研究をしています。

 

研究の過程で Semantic segmentation を学習し、"U-net"についてまとめました。

 

U-netはFCN(fully convolution network)の1つであり、画像のセグメンテーション(物体がどこにあるか)を推定するためのネットワークです。

 

この記事の対象者は機械学習の初学者〜中級者の方です。

 

そのため、前線で活躍されている方には有益ではありません。

 

この記事では、まずはGANについて簡単に把握して頂き、次に実際にどの様な例で使用するのかということをGoogle Colaboratoryで手を動かして頂ければ幸いです。

 

Google Colaboratoryの使い方は以下の記事でまとめています。

 

Google Colaboratory グーグルコラボラトリー グーグルコラボ 使い方
Google Colaboratoryの使い方【完全マニュアル】

続きを見る

 

また、実際にU-netを使用した教師なし機械学習をGoogle Colaboratoryで行った試行例は以下になります。実際にPythonのコードを動かして頂く事も可能です。

 

Google Colab
Google Colab

続きを見る

 

誤りがあった場合にはお問い合わせフォームにまでご連絡いただけましたら幸いです。

 

こちらのスライドに沿って解説させて頂きます。

 

U-Netを用いた細胞画像のセグメンテーションについて

この章から、U-Netを用いて、実際の細胞画像対してセグメンテーションを行う流れを解説させて頂きます。

この記事で扱うデータセットは多数の細胞核の画像です。

これらの画像は撮影時のさまざまな条件下でデータが取得されています。

そのため、データを確認すると、細胞の種類、倍率、およびイメージングモダリティが異なっている事が分かります。

医療現場では、さまざまなモダリティ機器が使用されています。たとえば、強い磁場と電波によって体の断層を撮影するMRI(磁気共鳴診断装置)は、代表的なモダリティです。これは、現場ではMRと呼ばれています。また、X線によって体の断層を撮影するCT(コンピュータ断層撮影装置)も、モダリティのひとつに含まれるものです。モダリティにはその他にも、同じくX線を使用して臓器や血管などを画像化するCR(コンピュータ・ラジオグラフィ)やDR(デジタルX線撮影装置)、XA(血管造影X線診断装置)、US(超音波診断装置)、ES(内視鏡装置)などがあります。

» 医療機器におけるモダリティ(Modality)とは

よって、これらの多種多様な画像を汎用的にセグメンテーションするというのはとても難度の高いタスクです。

この記事ではその難度の高いタスクに対するU-Netモデルの有効性を確認することをゴールとて設定し、U-Netを学習する方の一助になればと思っています。

実装の流れとしては、ネット上でも良く取り扱われている他のチュートリアルとほぼ同様に、以下の流れで進めます。

 実装の流れ

  1. データの確認、探索
  2. データの前処理
  3. U-Netのモデルの定義、トレーニング
  4. U-Netモデルの性能評価の確認

また、画像のアップロードや画像の処理やモデルのトレーニングを行う際に長い時間を要しますので、十分な時間を確保した上で以下を実行お願いします。(実際に、以下のコード実行は2時間ほどかかりました。)

また、モデルのトレーニングを行う場合はGPUの使用をお勧めします。

Google Colabを使う場合は上部『ランタイム』タブから『ランタイムのタイプを変更』を選択し、ハードウェアアクセラレータをGPUに変更をお願いします。

①  データの確認、探索

今回用いるデータセットは kaggle のコンペティションで用いられたデータセットを用います。 (https://www.kaggle.com/c/data-science-bowl-2018/data) 

もし本記事に記載されているコードを実行する場合は、上のサイトから一度お使いのパソコンにデータセットをダウンロードし、そのデータセットをこのcolabノートブック上にアップロードする必要があります。

方法については次のスライドを参考にして下さい。

 

トレーニングデータのzipファイルであるstage1_train.zipをアップロードしてから以下を実行してください。(アップロードは10分ぐらい時間がかかりました。)

まず、zipファイルの解凍を行います。

In[]

Out[]

U-netの使い方と具体的な実装方法について【細胞画像のSemantic segmentationを通して解説】

※ 出力内容の文字が潰れていてほぼ確認できないかもしれません。Google Colaboの方をご確認下さい。

次に、必要なライブラリをインポートしておきます。

In[]

続いてデータセットの読み込みを行います。

ここでは前処理の一部である画像のリサイズと、画像データ拡張も同時に行います。

画像のリサイズは様々なサイズの画像を全て固定のサイズに調整することにより1つのモデルによる対応が可能になります。

ここでは全ての画像を 256×256 の画像にリサイズしています。

また画像データ拡張は最近の画像系のディープラーニングの前処理とは一般的な処理で、画像に処理を加えることによりモデルの汎用化(予測精度を高める)ことが可能になります。

ここでは画像の正規化と水平垂直方向に画像をフリップさせる処理を追加しています。

「mask」はマスキング、つまり細胞のセグメンテーションがなされているデータであり、これが教師データとなります。

マスクに関しては今回は1つの細胞ごとに1つのファイルとなっているので、複数の画像を1つにまとめています。

トレーニングデータは一般的に入力画像と教師データ(mask)をペアとしてまとめ、このペアにより学習を行います。pytorchではこれらをDatasetクラスを用いてまとめます。

In[]

In[]

一枚の画像データとマスクの次元を確認します。

In[]

Out[]

画像枚数を確認します。

In[]

Out[]

次に、入力画像とマスクのデータがどうなっているのか確認してみます。

In[]

Out[]
U-netの使い方と具体的な実装方法について【細胞画像のSemantic segmentationを通して解説】
左列が入力画像、右列がマスクデータとなっています。

左列で細胞がある箇所に右列でマスクがなされていることが確認できます。

U-Netは左の画像を入力した際に右のようなマスクされた画像データが出力できれば良いということになります。

②データの前処理

続いて評価データ作成のため、トレーニングデータの一部を評価データとして分割します。

またpytorchではミニバッチ処理ができるようにDataLoaderクラスを作成します。

In[]

Out[]

 

③U-Netのモデルの定義、トレーニング

続いてU-Netのモデルを実装します。モデルについては解説記事か以下のサイトをご参照ください。

» ResercherGate  

こちらのサイトを元に実装をしていきます。

個人的な印象として、U-Netモデルは細かい構成よりはモデルの全体構成から把握していった方が理解がしやすい印象です。

上記サイトのU-Netの解説記事にも記載している通り、以下の流れについてまず把握しましょう。

  1. FCNにあたる部分
  2. Up Samplingにあたる部分
  3. Skip Connectionにあたる部分

以上をまず把握します。

以下のコードコメント文にそれぞれがどこに該当するかを記載しています。

Skip Connection は torch.cat によりFCN時の出力と合わせています。

conv_bn_relu 関数は畳み込みとバッチ正規化と、活性化関数Reluをまとめています。

In[]

 

損失関数について

セマンティックセグメンテーションの損失関数としてはBCELoss(Binary Cross Entropy)をベースとしたDiceBCELossがよく用いられます。

詳細な説明とコードは下記のサイトに記載があります。

» Kaggle Loss Function Library-Keras & Pytorch

考え方としては IoU に近く、予測した範囲が過不足なく教師データとなる領域を捉えているほど損失が低くなります

In[]

セマンティックセグメンテーションの精度評価指標となるIoUのクラスを定義します。

In[]

続いてU-Netの学習を行います。

まずモデル、オプティマイザ、損失関数のインスタンス作成を行います。

1epoch学習ごとに評価データによる精度評価を行い、精度評価の結果が最高のモデルを best_model_path 配下に保存する形になっています。

In[]

Out[]

 

④U-Netモデルの性能評価の確認

学習と評価が終了しましたので、エポックごとの損失、精度の変化をグラフ化します。

In[]

以上の通り、epoch数が進むにつれて損失が減り、精度が向上していることがわかります。

これは機械学習においてはモデルの学習が進み、より汎化性能(予測性能)が増して行っていることを意味しています。

次に、作成した学習したモデルを利用して、実際のモデルによるセマンティックセグメンテーションの結果を表示してみます。

まず作成したモデルを読み込みます。

In[]

続いて入力画像と教師データ、モデルによる出力を表示する関数を用意し、出力を行います。

In[]

Out[]

U-netの使い方と具体的な実装方法について【細胞画像のSemantic segmentationを通して解説】

U-netの使い方と具体的な実装方法について【細胞画像のSemantic segmentationを通して解説】

 

以上の結果を確認してみます。

Label Mask(教師データ)とPredicted Mask(モデル予測データ)を比較すると完全に等しくはなりませんが、モデルは比較的教師データに近いセグメンテーションをしていることがわかります。

U-Netはピクセルごとの画像の濃淡を元にセグメンテーションしているので、教師データより細かいセグメンテーションを行なっていることも分かるかと思います。

また、今回用いた学習データは数百枚のトレーニングデータしか用いておらず、(タスクにもよりますが)CNNなどで必要となるトレーニングデータの量と比べるととても少ないと感じられると思いますが、実際にデータ数が少ない時にも有用な方法です。(自分の研究ではそうでした。)

作成したモデルは保存していますので、このモデル再使用することでお手持ちの別の画像にもセグメンテーションをすることができますので、是非色々試して考察を行なって頂ければ幸いです。

今回は以上となります。

 

関連記事 【入門から上級レベルまで】AI•機械学習におすすめの本25選

関連記事 無料あり:機械学習エンジニアの僕がおすすめするAI(機械学習)特化型プログラミングスクール3社


-AI
-, , ,

Copyright© Tommy blog  , 2021 All Rights Reserved.