facenet-pytorch のインストールと動作確認(顔認識)(PyTorch,Python 3.12 を使用)(Windows 上)

次で配布されているソフトウェア

https://github.com/timesler/facenet-pytorch

これは,PyTorch による顔検出(MTCNN)と顔認識(InceptionResnetV1)のソフトウェアである.VGGFace2,CASIA-Webface で学習済みのモデルが提供されており,追加の学習を行わずに顔検証・顔識別に利用できる.

ソフトウェア等の利用条件等は,利用者で確認すること.

前準備

Python 3.12 のインストール(Windows 上) [クリックして展開]

以下のいずれかの方法で Python 3.12 をインストールする。Python がインストール済みの場合、この手順は不要である。

方法1:winget によるインストール

管理者権限のコマンドプロンプトで以下を実行する。管理者権限のコマンドプロンプトを起動するには、Windows キーまたはスタートメニューから「cmd」と入力し、表示された「コマンドプロンプト」を右クリックして「管理者として実行」を選択する。

winget install -e --id Python.Python.3.12 --scope machine --silent --accept-source-agreements --accept-package-agreements --override "/quiet InstallAllUsers=1 PrependPath=1 AssociateFiles=1 InstallLauncherAllUsers=1"

--scope machine を指定することで、システム全体(全ユーザー向け)にインストールされる。このオプションの実行には管理者権限が必要である。インストール完了後、コマンドプロンプトを再起動すると PATH が自動的に設定される。

方法2:インストーラーによるインストール

  1. Python 公式サイト(https://www.python.org/downloads/)にアクセスし、「Download Python 3.x.x」ボタンから Windows 用インストーラーをダウンロードする。
  2. ダウンロードしたインストーラーを実行する。
  3. 初期画面の下部に表示される「Add python.exe to PATH」に必ずチェックを入れてから「Customize installation」を選択する。このチェックを入れ忘れると、コマンドプロンプトから python コマンドを実行できない。
  4. 「Install Python 3.xx for all users」にチェックを入れ、「Install」をクリックする。

インストールの確認

コマンドプロンプトで以下を実行する。

python --version

バージョン番号(例:Python 3.12.x)が表示されればインストール成功である。「'python' は、内部コマンドまたは外部コマンドとして認識されていません。」と表示される場合は、インストールが正常に完了していない。

NVIDIA製GPUを使用する場合,NVIDIA ドライバのインストールが必要である.PyTorch の GPU 版パッケージには CUDA の実行時ライブラリが同梱されているため,NVIDIA CUDA ツールキットや cuDNN を別途システムにインストールする必要はない.

【サイト内の関連ページ】

PyTorch,facenet-pytorch のインストール

コマンドプロンプトを管理者として実行し,次のコマンドを実行する.

NVIDIA製GPU搭載のパソコンで,CUDA 12.6 を使用する場合.

python -m pip install -U torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cu126
python -m pip install -U facenet-pytorch

GPU を使用しない場合(CPU 版).

python -m pip install -U torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cpu
python -m pip install -U facenet-pytorch
使用しているGPUに対応するCUDAのバージョンは,PyTorch 公式サイトのインストール案内ページで確認できる.

facenet-pytorch のインストールと動作確認(顔認識)(Windows 上)

Windows での手順を下に示す.Ubuntu でも同様の手順になる.

  1. Windows で,コマンドプロンプトを管理者として実行.
  2. 顔画像データの準備

    %HOMEPATH%\facedata\images のようなディレクトリを作り,顔識別のためのデータベースとして使用する顔写真のファイル(1人につき1枚以上)を格納する.

    mkdir %HOMEPATH%\facedata\images
    
  3. 判定対象の画像を確認する

    判定したい画像(例:camera_0.jpg)を,同じく %HOMEPATH%\facedata\images の下に格納する.

  4. デモプログラムを実行する

    このプログラムは,データベースに登録した顔画像との類似度をもとに,判定対象の画像が誰なのかを顔認識する.

    次のPython プログラムを実行する.

    import os
    import torch
    from PIL import Image
    from facenet_pytorch import MTCNN, InceptionResnetV1
    
    def main():
        image_dir_path = os.path.expanduser(r"~\facedata\images")
    
        device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
    
        # 顔検出(MTCNN)と顔埋め込み(InceptionResnetV1,VGGFace2 で学習済み)の準備
        mtcnn = MTCNN(image_size=160, margin=0, device=device)
        resnet = InceptionResnetV1(pretrained='vggface2').eval().to(device)
    
        def get_embedding(image_path):
            img = Image.open(image_path).convert('RGB')
            face = mtcnn(img)
            if face is None:
                return None
            return resnet(face.unsqueeze(0).to(device)).detach().cpu()
    
        # データベースの構築(画像ファイル名から人物名を作成)
        database = {}
        for filename in os.listdir(image_dir_path):
            name, ext = os.path.splitext(filename)
            if ext.lower() not in ('.jpg', '.jpeg', '.png'):
                continue
            if name.startswith('camera'):
                continue
            embedding = get_embedding(os.path.join(image_dir_path, filename))
            if embedding is not None:
                database[name] = embedding
    
        def verify(image_path, identity_claim, database, threshold=0.9):
            embedding = get_embedding(image_path)
            if embedding is None or identity_claim not in database:
                return None, False
            dist = (embedding - database[identity_claim]).norm().item()
            return dist, dist < threshold
    
        def who_is_it(image_path, database, threshold=0.9):
            embedding = get_embedding(image_path)
            if embedding is None:
                return None, None
            best_name, best_dist = None, None
            for name, db_embedding in database.items():
                dist = (embedding - db_embedding).norm().item()
                if best_dist is None or dist < best_dist:
                    best_dist, best_name = dist, name
            if best_dist is not None and best_dist < threshold:
                return best_dist, best_name
            return best_dist, None
    
        # 判定対象の画像が,特定の人物であるかどうかを検証
        dist, is_valid = verify(os.path.join(image_dir_path, "camera_0.jpg"), "younes", database)
        print('camera_0.jpg is' + (' ' if is_valid else ' not ') + 'younes')
    
        # 判定対象の画像が,データベース中のどの人物であるかを識別
        dist, identity = who_is_it(os.path.join(image_dir_path, "camera_0.jpg"), database)
        if identity is None:
            print('camera_0.jpg is not found in database')
        else:
            print('camera_0.jpg is ' + str(identity))
    
    if __name__ == '__main__':
        main()
    
  5. 実行結果を確認する.

    顔認識の結果が表示される.