入力形状の変更¶
OpenVINO™ を使用すると、アプリケーションの実行中にモデルの入力形状を変更できます。これは、モデルの入力形状と異なるサイズの入力をモデルに供給する際に便利です。次に、モデルの入力形状を繰り返し変更する必要がある場合の手順を説明します。
reshape メソッド¶
reshape メソッドは、C++ では ov::Model::reshape
、Python では Model.reshape として使用されます。このメソッドは入力形状を更新し、それをすべての中間レイヤーを介してモデルの出力に伝達します。以下のコードは、reshape
メソッドを使用して新しいバッチサイズを設定する例です。
model.reshape([8, 3, 448, 448])
model->reshape({8, 3, 448, 448});
以下の図は、このメソッドを使用してモデル入力のサイズが画像入力によって変更される結果を示しています。
reshape
メソッドを使用する場合、次のいずれかのアプローチを実行できます。
-
単一の入力でモデルの入力形状を変更するため、新しい形状をメソッドに渡すことができます。以下に、入力画像に空間次元を適合する例を示します。
image = get_image() model.reshape([1, 3, image.shape[0], image.shape[1]])
// Read an image and adjust models single input for image to fit cv::Mat image = cv::imread("path/to/image"); model->reshape({1, 3, image.rows, image.cols});
逆に、モデルの入力形状に合わせて入力画像のサイズを変更するには、前処理 API を使用します。
-
ポート、インデックス、テンソル名による入力を指定して、再形状を表現できます。
openvino.runtime.Output
辞書キーは、実際の入力オブジェクトを渡して入力を指定します。新しい形状を表す辞書値はPartialShape
になります。port_to_shape = dict() for input_obj in model.inputs: shape = input_obj.get_partial_shape() # modify shape to fit your needs # ... port_to_shape[input_obj] = shape model.reshape(port_to_shape)
map<ov::Output<ov::Node>, ov::PartialShape
で実際の入力ポートを渡して入力を指定します。std::map<ov::Output<ov::Node>, ov::PartialShape> port_to_shape; for (const ov::Output<ov::Node>& input : model->inputs()) { ov::PartialShape shape = input.get_partial_shape(); // Modify shape to fit your needs // ... port_to_shape[input] = shape; } model->reshape(port_to_shape);
int
辞書キーは、そのインデックスで入力を指定します。新しい形状を表す辞書値はtuple
になります。idx_to_shape = dict() i = 0 for input_obj in model.inputs: shape = input_obj.get_partial_shape() # modify shape to fit your needs # ... idx_to_shape[i] = shape i += 1 model.reshape(idx_to_shape)
map<size_t, ov::PartialShape>
は、インデックスで入力を指定します。size_t i = 0; std::map<size_t, ov::PartialShape> idx_to_shape; for (const ov::Output<ov::Node>& input : model->inputs()) { ov::PartialShape shape = input.get_partial_shape(); // Modify shape to fit your needs // ... idx_to_shape[i++] = shape; } model->reshape(idx_to_shape);
str
辞書キーは、そのインデックスで入力を指定します。新しい形状を表す辞書値はstr
になります。name_to_shape = dict() for input_obj in model.inputs: shape = input_obj.get_partial_shape() # input may have no name, in such case use map based on input index or port instead if len(input_obj.get_names()) != 0: # modify shape to fit your needs # ... name_to_shape[input_obj.get_any_name()] = shape model.reshape(name_to_shape)
map<string, ov::PartialShape>
は、インデックスで入力を指定します。std::map<std::string, ov::PartialShape> name_to_shape; for (const ov::Output<ov::Node>& input : model->inputs()) { ov::PartialShape shape = input.get_partial_shape(); // input may have no name, in such case use map based on input index or port instead if (!input.get_names().empty()) { // Modify shape to fit your needs // ... name_to_shape[input.get_any_name()] = shape; } } model->reshape(name_to_shape);
reshape
メソッドの使用シナリオは、Hello Reshape SSD サンプルにあります。
注
状況によっては、モデルを再形成する準備ができていないことがあります。その場合、モデル変換 API や reshape
メソッドを使用して新しい入力形状を設定することはできません。
set_batch メソッド¶
モデルバッチの意味はモデルの設計によって異なる場合があります。モデルのバッチ次元を変更するには、レイアウトを設定し、set_batch
メソッドを呼び出します。
model.get_parameters()[0].set_layout(ov.Layout("N..."))
// Mark up batch in the layout of the input(s) and reset batch to the new value
model->get_parameters()[0]->set_layout("N...");
set_batch
メソッドは reshape 機能の高レベル API であるため、reshape
メソッドの影響に関するすべての情報は set_batch
にも当てはまります。
モデルの入力形状を設定したら、compile_model
メソッドを呼び出して、更新された形状で推論するため CompiledModel
オブジェクトを取得します。
OpenVINO ランタイムの IR 生成またはモデル表現のステージで、モデル入力形状を変更するアプローチもあります。
重要
形状変更機能を使用することで、動的モデル入力を静的モデル入力に変換したり、その逆を行うことができます。データの形状が推論ごとに変化しない場合、常に静的形状を設定します。静的形状を設定すると、使用するハードウェア・プラグインとモデルによって異なることがある動的形状のメモリーとランタイムのオーバーヘッドを回避できます。詳細は、動的形状を参照してください。
関連情報¶
拡張性ドキュメント - カスタム操作の形状推論のサポートを追加できる OpenVINO の特殊メカニズムについて説明します。
ov::Model::reshape - OpenVINO ランタイム C++ API 内。
Model.reshape - OpenVINO ランタイム Python API 内。