次の方法で共有


Windows ML のパフォーマンスとメモリ

この記事では、Windows Machine Learning を使用するときにアプリケーションのパフォーマンスを管理する方法について説明します。

スレッド処理とコンカレンシー

ランタイムから公開されるすべてのオブジェクトは アジャイルです。つまり、任意のスレッドからアクセスできます。 アジャイルの詳細については、 C++/WinRT のアジャイル オブジェクトを参照してください。

使用する 1 つの重要なオブジェクトは 、LearningModelSession です。 このオブジェクトは常に任意のスレッドから呼び出しても安全です。

  • GPU セッションの場合: オブジェクトは同時呼び出しをロックおよび同期します。 コンカレンシーが必要な場合は、それを実現するために複数のセッションを作成する必要があります。

  • CPU セッションの場合: オブジェクトはロックされず、1 つのセッションで同時呼び出しを許可します。 独自の状態、バッファー、およびバインド オブジェクトを管理するように注意する必要があります。

シナリオにおける目標を慎重に測定するようにしてください。 最新の GPU アーキテクチャは、CPU とは動作が異なります。 たとえば、待ち時間が短い場合は、コンカレンシーではなくパイプライン処理を使用して、CPU エンジンと GPU エンジン全体で作業をスケジュールする方法を管理できます。 マルチエンジン同期に関するこの記事 は、作業を開始するのに最適な場所です。 スループットが目標である場合 (可能な限り多くのイメージを一度に処理するなど)、CPU を飽和させるために複数のスレッドとコンカレンシーを使用することがよくあります。

スレッド化とコンカレンシーに関しては、実験を実行し、タイミングを測定する必要があります。 目標とシナリオに応じて、パフォーマンスが大幅に変化します。

メモリ使用率

LearningModel とLearningModelSession の各インスタンスには、メモリ内のモデルのコピーがあります。 小規模なモデルを使用している場合は気にならないかもしれませんが、非常に大きなモデルを使用している場合は、これが重要になります。

メモリを解放するには、モデルまたはセッションで Dispose を呼び出します。 一部の言語では遅延ガベージ コレクションが実行されるので、削除するだけで済まさないでください。

LearningModel は、新しいセッションの作成を可能にするために、コピーをメモリに保持します。 LearningModel を破棄すると、既存のすべてのセッションが引き続き機能します。 ただし、その LearningModel インスタンスで新しいセッションを作成することはできなくなります。 大規模なモデルの場合は、モデルとセッションを作成し、モデルを破棄できます。 Evaluate のすべての呼び出しに 1 つのセッションを使用すると、メモリ内に大規模なモデルの 1 つのコピーが作成されます。

Float16 のサポート

パフォーマンスを向上させ、モデルのフットプリントを減らすために、 ONNXMLTools を 使用してモデルを float16 に変換できます。

変換されると、すべての重みと入力が float16 になります。 float16 の入力と出力を操作する方法を次に示します。

  • ImageFeatureValue (画像機能値)

    • 推奨される使用方法。
    • 色とテンソル化されたデータを float16 に変換します。
    • bgr8 および 8 ビットイメージフォーマットをサポートし、データを失うことなく安全に float16 に変換できます。
  • テンソルフロート

    • 高度なパス。
    • float32 を float16 に型変換します。
    • 画像の場合、bgr8 はサイズが小さくて収まるので、これは安全に型変換できます。
    • イメージ以外の場合、 Bind は失敗し、代わりに TensorFloat16Bit を渡す必要があります。
  • TensorFloat16Bit (テンソルフロート16ビット)

    • 高度なパス。
    • float16 に変換し、float32 として入力を渡す必要があります。これは float16 にキャストダウンされます。

ほとんどの場合、演算子は引き続き 32 ビットの算術演算を実行します。 オーバーフローのリスクは少なく、結果は float16 に切り詰められます。 ただし、ハードウェアが float16 のサポートをアドバタイズする場合、ランタイムはそれを利用します。

入力データの前処理

WinML では、入力データの処理をより簡単かつ効率的にするために、いくつかの前処理手順が内部で実行されます。 たとえば、入力画像にはさまざまな色の形式や図形があり、モデルで想定されているものとは異なる場合があります。 WinML はイメージに対して変換を実行して一致させ、開発者の負荷を軽減します。

WinML では、ハードウェア スタック全体 (CPU、GPU など) も利用して、特定のデバイスやシナリオに最も効率的な変換を提供します。

ただし、特定の要件により、入力データを手動でテンソル化したい場合があります。 たとえば、画像に VideoFrame を使用したくない場合や、ピクセル値を 0 から 255 の範囲から 0 ~ 1 の範囲に正規化したい場合があります。 このような場合は、データに対して独自のカスタムテンソル化を実行できます。 この例については、 カスタムテンソル化のサンプル を参照してください。

Windows ML に関するヘルプについては、次のリソースを参照してください。

  • Windows ML に関する技術的な質問をしたり、質問に回答したりするには、Stack Overflowwindows-machine-learning タグを使用してください。
  • バグを報告するには、GitHub で問題を提出してください。