OpenCV でHaar分類器を自作してみる
昨年の12月に、OpenCV の バージョン3.1がリリースされました。画像認識の分野では、おそらく一番有名なプログラミング用ライブラリです。
OpenCVには、既に出来合いのHaar分類器があって、これを使うと、画像のどこに顔があるか認識できます。この分類器の認識精度に満足できない場合は、分類器を自作する必要があります。というわけで、試しに作ってみました。
分類器の自作にあたっては、「Create Your Own Haar Classifier for Detecting objects in OpenCV」というブロク記事と、「詳解 OpenCV -コンピュータビジョンライブラリを使った画像処理・認識-」という書籍を参考にしています。
Haar分類器とは?
Haar分類器は、教師あり機械学習手法の一つです。教師あり機械学習の場合、大量の正解画像(例えば、画像+顔の位置を表す矩形領域のXY座標)を予め人の手で用意しておいて、それを分類器の入力データとして与えます。そうすると、顔の位置を特定する為に最適な”パラメーター”を求めます。このパラメーターを求めるプロセスが、いわゆる「学習」に相当します。
パラメーターとは、-0.29384 とか、 2.3734509882 といった実数の集まりです。使う分類器の種類によって、パラメーターの意味合いは変わります。人間がその数字を見ても、デタラメな数にしか見えません。正解画像を1枚ずつ与えていくと、パラメーターの個数は変わらずに各々の値だけが刻々と変化します。値だけ眺めていても、どれくらいの認識精度を実現できそうなのか、さっぱり分かりません。テスト画像を実際に分類器にかけてみて、初めて精度を実感できます。
Haar分類器の作り方
Haar分類器で「顔」の位置を特定するデモはよく見かけるので、今回は少しひねって「目」の位置を特定してみます。
一般的に、Haar分類器は、最低でも1000枚単位の正解画像が必要だと言われています。前述のブログ記事を参考に、以下の手順で正解画像を用意しました。
- 動画撮影(Webカメラで自分を撮影)
- 動画の各フレームをbmp画像化(このやり方だと、一度に大量の画像が作れます。ffmpegを使いました)
- それらの画像から、目の位置をマウスで囲む(下の画像の赤い四角形)
黙々と作業すること20分、なんとか200枚作成できました。この生産性だと、1000枚作るのに約1時間半、ひたすら自分の顔が映った画像と向き合わねばならず、なかなか辛いです(笑)。ということで、1000枚集めるのは早々に諦めました。
実験結果
以下が、正解画像10枚の結果です。丸の箇所を「目」の位置と認識しています。
以下、100枚の場合。
以下、200枚の場合。
正解画像の増加に比例して、検出漏れが少し減り、誤検出が”激増”しました。この作業の延長線で1000枚集めても、シャボン玉で埋め尽くされる残念な結果になる気がします。
今後の課題
正解画像の集め方とか、正解画像の前処理とか、学習方法とか、識別アルゴリズムの種類とか、チューニングすべきポイントは山ほどあります。今回は、チューニングを一切考慮しないでHaar分類器を作るとどうなるか?という実験でもありました。
今後は、少しずつチューニングを施して、どこをいじるとどれくらい効果的なのか、検証していきたいと思います。