写真から顔部分を切り取る方法

提供: omotenashi-mind
移動先: 案内検索




ディープラーニングによる人物判定トレーニングを行うためにはある程度の数の顔写真を人物ごとに用意する必要があります。
が、いちいち手で顔部分を取り出す作業はやりたくないので、なんとか自動でトレーニング用データを準備する方法を模索します。

準備するもの

  • 認識させたい人物が写った写真をたくさん
  • Python 3.3+ もしくは Python 2.7がインストールされたLinux端末


Face Recognition 導入・顔抽出

画像から人の顔部分を検出するための方法として、「Face Recognition」を利用します。
dlibをベースとした顔識別ライブラリです。まずは導入します。

Face Recognition導入に必要なライブラリ一式の導入

sudo apt-get install build-essential cmake
sudo apt-get install libgtk-3-dev
sudo apt-get install libboost-all-dev


Face Recognition導入

必要ライブラリの準備ができたら、Face Recognition本体の導入です。

sudo pip install face_recognition

以上で準備完了です。

写真データからの顔写真エリア抽出

ここではimagesフォルダ配下に抽出対象の写真が複数枚収められているとします。複数画像から顔が写っているであろうエリアを抽出します。顔部分の検出には「face_detection」コマンドが利用できます。

face_detection --model cnn ./images

これにより、以下のような結果が得られます。

./images/IMG_0001.jpg,223,1571,1068,726
./images/IMG_0002.jpg,245,521,409,357
...

検査した画像のパスの右に、4つの数字が得られます。それぞれ、top, right, bottom, leftの座標を示します。この4つの点で囲まれた部分が顔があるエリアと判定されたエリアです。
実際に判定されたエリアを切り出すには、例えば「convert」コマンドを利用します。

指定範囲の切り取り

convert IMG_0001.jpg -crop 845x845+726+223 cropped_001.jpg

切り出すエリアを指定するには、cropオプションの後に "[幅]x[高さ]+[左上 x座標]+[左上 y座標]"といった形で指定すると無事に
顔と検出されたエリアが切り取れるはずです。

写真データから複数の顔写真を抽出する

face_detectionコマンドでは写真1つから代表1つのエリアのみ顔エリアの抽出が可能なようです。複数のエリアを抽出したい場合はPython上でface_locationsファンクションを利用すれば可能です。

import face_recognition
(...途中省略)
image = face_recognition.load_image_file(image_path)
face_locations = face_recognition.face_locations(image, model="cnn")


注意すべきは、

  • 1280x720くらいの画像サイズが望ましい。
    • 大きすぎる解像度ではメモリがいくらあっても足りません。。(24GBメモリでもOOM)
  • 画像の回転方向を正しくしないと正しい結果は得られません。


画像サイズを1280x720くらいの解像度まで落としても、TensorFlowの学習によって十分なトレーニング結果が得られました。