2013年3月10日日曜日

EMアルゴリズム 〜OpenCVによる実践〜

in English

はじめに

先のページでEMアルゴリズムの理論をまとめた。今回は、OpenCVにあるEMアルゴリズムの実装を使い、類似色による領域分割を行う。この際、先の解説で定義した量との対応付けも行う。

表式一覧

OpenCVが計算する量との対応付けを行うため、先のページにある表式を再掲しておく。

最大化すべき尤度は次式で定義される。

ここで、 は規格化されたガウス関数であり、 は観測点、 は平均値ベクトル、 は共分散行列である。 は各ガウス関数の重みである。 また、EMアルゴリズムでは以下の量も使用した。




プログラム

main関数は以下の通りである。考える空間はRGB色空間であり、画像上の各画素値が観測点となる。すなわち、 である。 は全画素数に相当する。
  1. 3-6行目:入力画像を読み込む(image)。画像の型を確認し、変数image_rowsimage_colsを定義する。
  2. 10-13行目:imageの形状を変更し、reshaped_imageを作る。型、行数、列数を確認する。
  3. 16-20行目:reshaped_imageの型を変更し、samplesを作る。型、行数、列数を確認する。samplesはEMアルゴリズムの入力となる。
  4. 22-23行目:EMアルゴリズムcv::EMのインスタンスを作成する。cv::EMのコンストラクタの引数は以下の通りである。
    • 第1引数:ガウス関数の個数
    • 第2引数:共分散行列のタイプ
    • 第3引数:アルゴリズムの停止条件
    第1引数は に相当する。 今回の実装では、第1引数以外はデフォルト値を利用した。第2引数のデフォルト値は、EM::COV_MAT_DIAGONALであり、これは正の値を成分として持つ対角行列を意味する。すなわち、未知数はD個である。ここで、Dは観測点の定義される空間の次元である。いまの場合、3である。
  5. 26-28行目:出力値を格納する行列を用意する。
  6. 31行目:EMアルゴリズムを実行する。 関数trainは、初期状態を生成するため、K-meansクラスタリングを実行する。
  7. 33-35行目:出力値log_likelihoodsの型、行数、列数を確認する。各行には以下の量が格納されている。
  8. 37-39行目:出力値labelsの型、行数、列数を確認する。 labelsには以下の量が格納される。
    (以下の記述を修正しました。2013/3/21)

    ここで、


    とした。 は観測点の実現確率である。


  9. 41-44行目:出力値probsの型、行数、列数を確認する。probsには が格納される。関数observe_probsについては後述する。
  10. 46-50行目:出力値meansの型、行数、列数を確認する。 が格納されている。RGB空間を考えているので、これは3次元ベクトルである。関数observe_labels_and_meansについては後述する。
  11. 52-56行目:出力値weightsの型、行数、列数を確認する。ここには が格納されている。 関数observe_weightsについては後述する。
関数observe_probsは以下の通りである。
  1. 13行目:以下の等式を確認している。
  2. 16行目:以下の等式を確認している。
関数observe_weightsは以下の通りである。
  1. 10行目:以下の等式を確認している。
関数observe_labels_and_meansは以下の通りである。この関数では、各点(各画素)に割り振られたラベルkを、それに対応する平均値ベクトル に置き換えている。
  1. 4行目:最終結果を収める行列rgb_imageを作る。
  2. 9-11行目:meansはcluster_number x 3の行列である。ここで3は空間の次元である。各行にはガウス関数の中心座標(平均値ベクトル)が収められている。meansの要素の型を浮動小数点から0から255までのstd::uint8_tへ変更する。さらに、チャンネル数を3に変更する。
  3. 13-18行目:ラベルの値を(B,G,R)に置き換え、最終画像rgb_imageを作る。

結果

cluster_num=2
cluster_num=3

cluster_num=5
cluster_num=10
元画像

開発環境

  1. Mac OS X 10.8.2
  2. プロセッサ:3.06 GHz Intel Core 2 Duo
  3. メモリ:4GB
  4. Xcode4.6 with Apple LLVM 4.2(C++ Language Dialect → GNU++11, C++ Standard Library → libc++)
  5. boost-1.51.0(Apple LLVM 4.1でコンパイルしたもの。こちら
  6. opencv-2.4.3(Apple LLVM 4.2でコンパイルしたもの。こちら

参考文献

  1. Pattern Recognition and Machine Learning, Christopher M. Bishop, Springer
  2. OpenCVドキュメント

1 件のコメント:

  1. 1年以上前の記事ですが・・・
    Web上にOpenCVのEMアルゴリズムの文献が少なく、大変助かりました。
    ありがとうございます。

    返信削除