顔検出を仕切り直し

 もうアプリの完成なんて眼目にもなく、顔(パーツ)検出に集中しています。
 
 前回、総理に眼鏡ヒゲを付けさせていただいたのですが、全般的に検出率が悪いのですね。7割そこそこといったところ。
 
 モザイクにして16階調モノスケールにしていたのですが、256階調にしても計算量は変わらない。
 戻したところ、ちょっと検出率向上。
 
 また、試しにRGB成分ごとに検出してみたらR>G>Bの順に差が出たので、グレースケール化の

color = (int)(r*0.298912 + g*0.586611 + b*0.114478);

color = (int)(r*(0.298912+0.3) + g*(0.586611-0.2) + b*(0.114478-0.1));

に変更。+0.3、-0.2、-0.1 の補正値は適当です。
 これが、こう変わりました。美白化ですね(赤味を強くした)。
device-2015-02-28-165702 device-2015-02-28-165808
ちょっと検出率向上。
 
 でも、顔が大き過ぎたり小さ過ぎたり、上過ぎたり下過ぎたりで、検出率には限界があるのですね。
 
 仕切り直ししました。
 
 はじめに顔の位置や大きさを知りたいので、R成分を抜き出してみる。

color = r*2 – g – b;
if(color < 0) color = 0; この値をRGBに入れるので、黒白グレーなど赤くない色は、黒くなるといった次第。 device-2015-02-28-165934
 気持ち悪いけど、こうなります。
 
 このままでは処理しにくいので、4階調にして

color = ((int)(color/64f))*64;

 更に、上3階調分を白くして2階調にしちゃう。

if(color > 0) color = 255;
device-2015-02-28-170046 device-2015-02-28-170141

 この画像を使って位置と大きさを求めるのですが、白黒の境を走査してもゴミも拾っちゃいそうだったので、とても好きなモンテカルロ法を導入。

 画面上に適当に 2000 発の点を打ち込み、その場所が「白」ならば上下左右に走査し「黒」になったらマークします。
 最後に上下左右端から走査して、規定値(10マーク)以上のラインを顔の位置としたものです。
 耳の端っことか、背景の赤部分を拾い難くしたわけですね。
 
 更に、検出した顔エリアの横中央付近で一番明るいラインを いろいろやって(省略)検出してみました。

 そのラインを基に瞳検出器を当てた結果が次のとおりです(R成分画像に重ねてみました。気持ち悪い画像が続きますがご容赦を。中央縦ラインは、瞳検出後にその中間点に引いた線なので、あまり意味がありません)。

 まずは、合格者から
ok1
ok2
 副大臣たちも参加し
ok3
ok4
 44名合格です。

 そして、残念ながらの不合格者は
ng
 8名。コワい大統領が入ってしまったのが悔やまれます。

 検出率 約 84 %です。良くはなりました。
 この内4名は、顔エリアの中央に瞳が検出されてしまったケースなので拾い上げて補正できそうかな。

 おじさん顔に相当にフィッティングしてしまったとも思われるので、女子のサンプルも加えつつ、まだまだ続きます。

 今宵はジンフィズを嗜んでいるので、これまで。