Core MLモデルを連結してひとつのモデルにするパイプライン機能
Core MLのパイプライン機能
パイプライン(Pipeline)は複数のCore MLモデルを繋げてひとつのモデルのように扱うことができる機能です。
たとえばfoo.mlmodel
とbar.mlmodel
という2つ(以上)のモデルがあり、次のようにモデルfoo
の出力をモデルbar
の入力として使っているような場合に、
2つのモデルを結合させたパイプラインモデルfoobar.mlmodel
を作ると、次のようにひとつのモデルで処理することができるようになります。
これにより以下のようなメリットが考えられます。
- パフォーマンス(CPU・GPU間で入出力データやコマンドをやりとりする回数が減る)
- モデルの扱い(モデル利用側での実装)がシンプルになる
- モデルサイズがトータルで小さくなる(Linked Model [1]を使用する場合)
- iOS/macOSビルトインの特徴抽出器であるVision Feature Print や Audio Feature Print について理解できる [2]
coremltools.models.pipeline
coremltools
にはパイプラインに関連するAPIをまとめた
coremltools.models.pipeline
モジュール[3]が用意されています。
パイプラインの種類
パイプラインモデルを表すクラスとして、次の3つがあります。
クラス | 概要 |
---|---|
PipelineClassifier |
分類モデルとしてふるまうパイプラインモデル |
PipelineRegressor |
回帰モデルとしてふるまうパイプラインモデル |
Pipeline |
その他の種類の推論を行うパイプラインモデル |
本章では例として、PipelineClassifier
型のパイプラインモデルを構築する手順を紹介します。
パイプラインの構築手順
PipelineClassifierオブジェクトの生成
PipelineClassifier
のクラス定義はこうなっています。
class coremltools.models.pipeline.PipelineClassifier(
input_features,
class_labels,
output_features=None,
training_features=None
)
引数input_features
とclass_labels
は必須で、input_features
には入力の名前と型のタプル((‘name’, datatype)
)を配列で渡します。class_labels
にはクラスラベルとなる配列を渡します。output_features
は指定しなければデフォルトの名前("classProbability"
)になります。以下に例を示します。
from coremltools.models.pipeline import *
from coremltools.models import datatypes
input_features = [ ("hoge", datatypes.String()) ]
pipeline = PipelineClassifier(input_features, labels)
パイプラインにモデルを追加
add_model
メソッドでモデルを追加していきます。MLModel
オブジェクトまたはspec(Model_pb2.Model
)オブジェクトが渡せます。
pipeline.add_model(foo_model)
pipeline.add_model(bar_model)
add_model
で追加した順にモデルがパイプラインとして結合されていきます。ここで重要な点として、追加するモデルの入力が、パイプラインのinput_features
と(名前と型が)一致するか、パイプライン内の前のモデルの出力と一致する必要があります。
たとえば上の例でいうと、foo_model
の入力は名前が"hoge"
、型が文字列である必要があり、bar_model
の入力の名前と型はfoo_model
の出力の名前と型と一致する必要があります。
MLModelオブジェクト生成
PipelineClassifier
オブジェクトのSpecから、MLModel
オブジェクトを生成できます。
pipeline_model = coremltools.models.MLModel(pipeline.spec)
可視化や保存等、MLModel
オブジェクトの取り扱いについては参考書籍を参照してください。
パイプラインモデルとVision Feature Print
Create MLが生成する画像分類モデルは、特徴抽出モデル+画像分類モデルの2つのモデルから構成されるパイプラインモデルとなっています。
その特徴抽出部を担うのが Vision Feature Print
と呼ばれるiOSにビルトインされているモデルです。
詳細はこちらの記事で解説しています。
参考書籍
目次
第1章 準備
- 1.1 Core ML Toolsとは
- 1.2 Core ML Toolsの環境構築
第2章 Core ML Toolsはじめの一歩
- 2.1 2行のコードで学習済みモデルをロードする
- 2.2 2行のコードでCore MLモデルに変換する
- 2.3 変換したモデルを.mlmodelファイルとして保存
第3章 Core MLモデル作成の基礎
- 3.1 HDF5ファイルを読み込む
- 3.2 Core MLモデルに変換する
- 3.3 Core MLモデルの入力の型を変更する
- Core MLモデルから自動生成されるSwiftコード
- Visionはどのように画像分類モデルを判定するか?
第4章 オンデバイス学習 - UpdatableなCore MLモデルの作成
- 4.1 モデルのパーソナライゼーション
- 4.2 ベースとなるモデルの作成
- 4.3 Updatableなモデルに変換する
- 4.4 損失関数をセットする
- 4.5 最適化アルゴリズムをセットする
- 4.6 エポック数をセットする
- 4.7 モデルを保存する
第5章 オンデバイス学習 - iOSで学習
- 5.1 MLUpdateTask
- 5.1.1 mlmodelc
- 5.1.2 MLBatchProvider, MLArrayBatchProvider
- 5.1.3 MLTask
- 5.1.4 オンデバイスモデル更新タスクの全体感
- 5.2 学習データの準備
- 5.3 学習タスクの実行
- 5.4 オンデバイスで学習したモデルを保存する / MLUpdateContext, MLWritable
- 5.5 推論処理の実行
第6章 TensorFlowモデルの変換 - 基礎編
- 6.1 tfcoreml
- 6.2 tfcoremlを用いたCore MLモデルへの変換(最小実装)
- 6.2.1 学習済みモデル(.pbファイル)を読み込む
- 6.2.2 出力テンソルの名前を取得する
- 6.2.3 tfcoremlを用いて変換する
- 6.3 より扱いやすいCoreMLモデルに変換する
- 6.3.1 クラスラベルを指定する
- 6.3.2 入力の型を画像に変更する
- 6.4 iOSで推論を実行
- 6.5 入力画像の前処理を指定する
第7章 TensorFlowモデルの変換 - 画風変換モデル
- 7.1 学習済みモデルからグラフ定義を読み込む
- 7.2 変換に必要なグラフの情報を取得する
- 7.2.1 入力テンソルの名前を取得する
- 7.2.2 出力テンソルの名前を取得する
- 7.3 tfcoremlを用いて変換する
- 7.3.1 入力テンソルのshapeを指定する
- 7.4 Core MLモデルの出力の型を変更する
- 7.5 iOSで画風変換を実行
- 7.5.1 複数の入力を持つCore MLモデルをVisionで使う
- 7.5.2 出力画像を取得する
第8章 Flexible Shape - 超解像モデル
- 8.1 Flexible Shapeとは/使いどころ
- 8.2 超解像モデルをCore MLモデルに変換する
- 8.3 Flexible Shapeを適用する
- 8.4 iOS側での推論処理の実行
第9章 Core MLモデルのサイズを小さくする
- 9.1 本章で利用する感情認識モデルについて
- 9.2 重みを16ビット化する
- 9.2.1 16ビット化が推論結果の精度に与える影響
- 9.2.2 Core MLモデルを16ビット化する手順
- 9.3 クォンタイズ
- 9.4 iOSでの推論結果の比較
- 9.5 さらなるモデルサイズ削減
- 9.5.1 ルックアップテーブルを利用した量子化
- 9.5.2 モデルの一部を共通化
第10章 パイプラインモデルとリンクモデル(Linked Model)
- 10.1 パイプラインの構築
- 10.1.1 coremltools.models.pipelineモジュール
- 10.1.2 PipelineClassifierオブジェクトの生成
- 10.1.3 パイプラインにモデルを追加
- 10.1.4 MLModel オブジェクト生成
- 10.2 リンクモデル(LinkedModel)
- 10.2.1 リンクモデルとは/リンクモデルを使用するメリット
- 10.2.2 パイプラインとリンクモデル
- 10.2.3 リンクモデルの作成方法
- CreateMLのモデルはなぜ小さいのか
- CreateMLとパイプライン
- Vision FeaturePrint
第11章 モデルの可視化
- 11.1 Netron
- 11.2 coremltoolsのvisualize_spec
- 11.3 TensorBoard
- 11.3.1 TensorFlowモデルのグラフを可視化
- 11.3.2 Kerasでの学習状況を可視化
- 11.4 Kerasのplot_model
第12章 mlmodelファイルフォーマット
- 12.1 mlmodelファイルフォーマットを理解するメリット
- 12.2 .protoファイルの読み方
- 12.3 coremltoolsとprotobuf
- 12.4 protobuf API
付録A coremltools逆引きリファレンス
- A.1 MLModelオブジェクトを生成する
- .mlmodelファイルから生成する
- spec(Model_pb2.Model)から生成する
- A.2 モデルのspec(Model_pb2.Model)を取得する
- .mlmodelファイルから取得する
- MLModelオブジェクトから取得する
- A.3 .mlmodelファイルの保存・読み込み
- .mlmodelファイルを読み込む
- .mlmodelファイルとして保存する
- A.4 NeuralNetworkBuilderを生成する
- A.5 モデルの中身を調べる
- モデルを可視化(ビジュアライズ)する
- モデルのバージョン(Specification Version)を確認する
- モデルのdescriptionをログに出力する
- ネットワークの情報をログに出力する
- NeuralNetworkBuilderでモデルの入力・出力形式を確認する
- モデルのレイヤー一覧を出力する
- モデルの中間層の入出力形式を調べる
- A.6 Core MLモデルにクラスラベルを与える
- ラベル文字列の配列を渡す
- クラスラベルファイルのパスを渡す
- A.7 モデルの入力・出力をカスタマイズする
- 入力・出力名を指定する
- 変換時に入力の型を画像型にする
- 変換済みモデルの入力・出力の型を画像型にする
- 入力テンソルのshapeを指定する
- 入力画像の前処理を指定する
- A.8 モデルサイズを圧縮する
- 重みを16ビット(半精度)化する
- 重みをクォンタイズする
- A.9 オンデバイス学習関連
- モデルがUpdatableかどうかを調べる
- Updatableなレイヤー一覧を出力
- Updatableなモデルに変換する
- 学習で使用する損失関数をセットする
- 損失関数のサマリを確認する
- 学習で使用する最適化アルゴリズム(オプティマイザ)をセットする
- 最適化アルゴリズムを確認する
- エポック数をセットする
- A.10 FlexibleShape関連
- FlexibleShapeの適用可否を確認する
- 入力・出力の画像サイズを範囲で指定する
- 入力・出力に複数の画像サイズを指定する
- A.11 misc.
- 利用中のcoremltoolsのバージョンを確認する
-
パイプライン機能とVision Feature Printの関係については、拙著で詳しく解説しています。Audio Feature Printについてはこちらの記事で解説しています。 ↩︎
-
ドキュメントは apple.github.io/coremltools/source/coremltools.models.html#module-coremltools.models.pipeline に、ソースコードは
coremltools
リポジトリの models/pipeline.py にあります。 ↩︎
Discussion