ファイルフォーマットコンバーター¶
概要¶
ファイルフォーマットコンバーターを使うと、ONNX ファイルフォーマット、および NNabla C Runtime で Neural Network Libraries (または Console) ワークフローを実現できます。
ファイルフォーマットコンバーターには次のような機能があります。
NNP のバリエーションを有効な NNP へ変換する
ONNX から NNP へ変換する
NNP から ONNX へ変換する
NNP から NNB へ変換する (NNabla C Runtime のバイナリー形式)
Convert NNP to Tensorflow saved_model
Convert Tensorflow checkpoint, frozen graph or saved_model to NNP
Convert NNP to Tensorflow Lite
Convert NNP to INT8 quantized Tensorflow Lite
Convert Tensorflow Lite to NNP
試用段階: NNP から NNabla C Runtime の C ソースコードへ変換する
重要なお知らせ: 本ファイルフォーマットコンバーターには、いくつかの既知の問題が残っています。
サポートする ONNX オペレーターは制限されています。詳細は Function-Level Support Status をご覧ください。
サポートする Tensorflow operator は制限されています。詳細は Function-Level Support Status をご覧ください
NNP から C ソースコードへの変換はまだ試用段階です。動作しますが、十分にテストされていません。
アーキテクチャー¶
本ファイルフォーマットコンバーターは、中間形式として Neural Network Libraries 内に定義された protobuf を使います。
汎用のファイルフォーマットコンバーターではありませんが、Neural Network Libraries では指定されたコンバーターです。
本コンバーターは、ONNX ファイルに対する入力および出力を指定可能ですが、ONNX ファイルに Neural Network Libraries がサポートしない機能を含んでいる場合、変換中にエラーが発生する可能性があります。
また本コンバーターは、中間プロセス機能も提供します。詳細は、 プロセス をご覧ください。
Installation¶
Before using this converter, please use command pip install nnabla_converter
to install nnabla_converter.
Note that, flatbuffer package is necessary for TFLite export, please check Tensorflow Lite section in this page for more details.
変換¶
サポートするフォーマット¶
NNP¶
NNP は NNabla のファイルフォーマットです。
NNP フォーマットは データフォーマット に記述されます。
本ファイルフォーマットコンバーターでは、いくつかの NNP バリエーションでしか動作しません。
NNP 標準フォーマット (.nnp)
NNP ファイルの内容 (.nntxt, .prototxt, .h5, .protobuf)
ONNX¶
制限事項¶
学習はサポートしません。
Support operator set 7,9,10,11.
すべての機能をサポートしているわけではありません。詳細は Function-Level Support Status をご覧ください。
限られた Neural Network Console のプロジェクトのみサポートします。詳細は Model Support Status をご覧ください。
NNB¶
NNB is compact binary format for NNabla C Runtime. The file format is shown as the following diagram:
There are several concepts, such as buffer, variable, function, input and output in this file. Each of them is represented as a list. Each list is recorded with 2 members: number of object, and index in memory block table. The index points to the position in a memory block index table. The index in memory block index table points to the start address of memory data block.
It is designed for nnabla-c-runtime.
C ソースコード¶
ファイルフォーマットコンバーターは、 nnabla-c-runtime の C ソースコード出力をサポートします。
Tensorflow¶
制限事項¶
Bridged by onnx, tensorflow import and export is supported with some limitations.
- As for the importer, 4 formats tends to be supported:
.pb, tensorflow frozen graph フォーマット
.ckpt, tensorflow check point フォーマット version 1
.ckpt.*, tensorflow check point フォーマット version 2
saved_model, tensorflow saved_model format
As for the exporter, some of Neural Network Console projects are supported. See Model Support Status. The output of converter is tensorflow saved_model format.
Tensorflow Lite¶
制限事項¶
- For export to tensorflow lite, please install
flatbuffers
package: For Windows platform, download package from FlatBuffers and extract.
For Linux platform, use command
snap install flatbuffers
to install flatbuffers.For MaxOS platform, use command
brew install flatbuffers
to install flatbuffers.
and add the executable file flatc
to the system PATH.
After exporting TFLite, a json file with the same name will be generated, recording whether the input and output of the TFLite network need to be transposed to channel_last according to base_axis.
INT8 quantized Tensorflow Lite¶
制限事項¶
You should also install flatbuffers
package. Please refer to the installation above.
You need provide a represent dataset to the converter if you want to convert nnp to int8 quantized tflite.
Represent dataset is a subset of training dataset, about 2% - 10% of training data.
You can collect represent dataset in your training loop. It should be saved as numpy's .npy
format.
Here's an example:
rdataset = []
# suppose this is your training loop
for step in range(max_step):
image, label = dataset.next()
x.d = image
rdataset.append(image)
# your code
# ...
rdataset = np.array(rdataset).astype(np.float32)
np.save('represent_dataset.npy', rdataset)
Of course, you can create represent dataset by any way you like, but please ensure the shape of each item is equal with the shape of network's input and you have finished the necessary preprocess.
プロセス¶
繰り返しの拡張と循環¶
Neural Network Console は LoopControl
擬似関数である RepeatStart, RepeatEnd, RecurrentInput, RecurrentOutput または Delay をサポートしています。
現在、Neural Network Library ではこれらの関数を直接的にはサポートしていません。
ファイルフォーマットコンバーターは、ネットワークを拡張し、デフォルトでこれらの擬似関数を削除します。
これらの関数を保持したい場合、ファイル変換時にコマンドラインオプション --nnp-no-expand-network
を指定してください。
ネットワークを分割する¶
--split
オプションを使ってネットワークを分割できます。
この機能を使用する場合、 分割ネットワーク をご覧ください。
使い方¶
NNP 操作¶
NNP から NNP への変換¶
NNP から NNP への変換が必要な場合があります。
たいていの場合、繰り返しの拡張、あるいは循環ネットワークは Neural Network Console ではサポートしていますが、C++ API ではサポートしていません。
$ nnabla_cli convert input.nnp output.nnp
console 出力から単一の NNP ファイルへ変換する¶
Neural Network Console の現在のバージョンは .nntxt と .h5 を学習結果として出力します。
続いて、分離したファイルを単一の NNP に変換し、パラメータを protobuf 形式で格納する必要があります。
$ nnabla_cli convert net.nntxt parameters.h5 output.nnp
console 出力から単一の NNP ファイルへ 繰り返しの拡張や循環なしに変換する¶
$ nnabla_cli convert --nnp-no-expand-network net.nntxt parameters.h5 output.nnp
パラメータ形式を hdf5 で保持する¶
$ nnabla_cli convert --nnp-no-expand-network --nnp-parameter-h5 net.nntxt parameters.h5 output.nnp
すべてを単一の nntxt に入れる¶
$ nnabla_cli convert --nnp-parameter-nntxt net.nntxt parameters.h5 output.nntxt
ONNX 操作¶
NNP から ONNX へ変換する¶
$ nnabla_cli convert input.nnp output.onnx
onnx opset 9 出力を指定する場合、次のように指定してください (デフォルトは opset 7):
$ nnabla_cli convert input.nnp output.onnx -d opset_9
ONNX から NNP へ変換する¶
$ nnabla_cli convert input.onnx output.nnp
Currently, opset 7,9,10,11 are supported to import.
C Runtime 操作¶
一般的に、ファイルから C Runtime に変換するときは、バッチサイズを 1 に指定する方がよいとされています。バッチサイズが 1 より大きい場合、バッチサイズを 1 にするためにまとめて処理する必要があります。コマンドラインオプションで -b 1
を追加してください。
NNP から NNB へ変換する¶
$ nnabla_cli convert -b 1 input.nnp output.nnb
NNP から C ソースコードへ変換する¶
$ nnabla_cli convert -b 1 -O CSRC input.onnx output-dir
量子化¶
C-runtime ライブラリは、バイナリ (または固定小数点) の重みをサポートしており、モデル (およびフットプリント) のサイズを劇的に縮小できます。モデルを量子化する方法については、 固定小数点量子化によるネットワークの圧縮 を参照してください。
Tensorflow 操作¶
Convert NNP to Tensorflow saved_model¶
$ nnabla_cli convert input.nnp output_saved_model --export-format SAVED_MODEL
NNP から Tensorflow frozen graph へ変換する¶
$ nnabla_cli convert input.nnp output.pb
NNP から Tensorflow frozen graph へ変換する¶
$ nnabla_cli convert input.pb output.nnp
Tensorflow checkpoint から NNP へ変換する¶
checkpoint version 1 の場合:
$ nnabla_cli convert input.ckpt output.nnp --inputs x0,x1 --outputs y0,y1
input.ckpt と同じディレクトリには、 その関連ファイルである checkpoint、input.ckpt.meta などがあることが必要です。 inputs
では、モデルの入力名がコンマで区切られていることが必要です。 outputs
も同様です。checkpoint 形式の解析では、入力と出力があることが必要です。
checkpoint version 2 の場合:
$ nnabla_cli convert input.ckpt.meta output.nnp --inputs x0,x1 --outputs y0,y1
input.ckpt.meta と同じディレクトリには、その関連ファイルである checkpoint、 *.ckpt.index などがあることが必要です。
Convert Tensorflow saved_model to NNP¶
$ nnabla_cli convert input_saved_model output.nnp
Convert NNP to Tensorflow Lite¶
$ nnabla_cli convert -b 1 input.nnp output.tflite
Convert NNP to INT8 quantized Tensorflow Lite¶
$ nnabla_cli convert -b 1 input.nnp output.tflite --quantization --dataset represent_dataset.npy
Convert Tensorflow Lite to NNP¶
$ nnabla_cli convert input.tflite output.nnp
分割ネットワーク¶
分割ネットワークは少し複雑で面倒な場合があります。
NNP ファイルは複数の Executor ネットワークを持つことがありますが、Split は単一ネットワークを分割することしかサポートしません。
まず、NNP の中に executor がいくつあるかを確認し、どの executor を nnabla_cli dump
で分割するのか指定してください。
$ nnabla_cli dump squeezenet11.files/SqueezeNet-1.1/*.{nntxt,h5}
2018-08-27 15:02:40,006 [nnabla][INFO]: Initializing CPU extension...
Importing squeezenet11.files/SqueezeNet-1.1/net.nntxt
Importing squeezenet11.files/SqueezeNet-1.1/parameters.h5
Expanding Training.
Expanding Top5Error.
Expanding Top1Error.
Expanding Runtime.
Optimizer[0]: Optimizer
Optimizer[0]: (In) Data variable[0]: Name:TrainingInput Shape:[-1, 3, 480, 480]
Optimizer[0]: (In) Data variable[1]: Name:SoftmaxCrossEntropy_T Shape:[-1, 1]
Optimizer[0]: (Out)Loss variable[0]: Name:SoftmaxCrossEntropy Shape:[-1, 1]
Monitor [0]: train_error
Monitor [0]: (In) Data variable[0]: Name:Input Shape:[-1, 3, 320, 320]
Monitor [0]: (In) Data variable[1]: Name:Top5Error_T Shape:[-1, 1]
Monitor [0]: (Out)Monitor variable[0]: Name:Top5Error Shape:[-1, 1]
Monitor [1]: valid_error
Monitor [1]: (In) Data variable[0]: Name:Input Shape:[-1, 3, 320, 320]
Monitor [1]: (In) Data variable[1]: Name:Top1rror_T Shape:[-1, 1]
Monitor [1]: (Out)Monitor variable[0]: Name:Top1rror Shape:[-1, 1]
Executor [0]: Executor
Executor [0]: (In) Data variable[0]: Name:Input Shape:[-1, 3, 320, 320]
Executor [0]: (Out)Output variable[0]: Name:y' Shape:[-1, 1000]
上記の出力結果によって、1 つの executor のみがあることが分かります。
続いて nnabla_cli dump -E0
で executor の詳細情報を見ることができます。
$ nnabla_cli dump -E0 squeezenet11.files/SqueezeNet-1.1/*.{nntxt,h5}
2018-08-27 15:03:26,547 [nnabla][INFO]: Initializing CPU extension...
Importing squeezenet11.files/SqueezeNet-1.1/net.nntxt
Importing squeezenet11.files/SqueezeNet-1.1/parameters.h5
Try to leave only executor[Executor].
Expanding Runtime.
Executor [0]: Executor
Executor [0]: (In) Data variable[0]: Name:Input Shape:[-1, 3, 320, 320]
Executor [0]: (Out)Output variable[0]: Name:y' Shape:[-1, 1000]
-F
オプションにより、関数リストを取得できます。
$ nnabla_cli dump -FE0 squeezenet11.files/SqueezeNet-1.1/*.{nntxt,h5}
2018-08-27 15:04:10,954 [nnabla][INFO]: Initializing CPU extension...
Importing squeezenet11.files/SqueezeNet-1.1/net.nntxt
Importing squeezenet11.files/SqueezeNet-1.1/parameters.h5
Try to leave only executor[Executor].
Expanding Runtime.
Executor [0]: Executor
Executor [0]: (In) Data variable[0]: Name:Input Shape:[-1, 3, 320, 320]
Executor [0]: (Out)Output variable[0]: Name:y' Shape:[-1, 1000]
Executor [0]: Function[ 0 ]: Type: Slice Name: Slice
Executor [0]: Function[ 1 ]: Type: ImageAugmentation Name: ImageAugmentation
Executor [0]: Function[ 2 ]: Type: MulScalar Name: SqueezeNet/MulScalar
Executor [0]: Function[ 3 ]: Type: AddScalar Name: SqueezeNet/AddScalar
Executor [0]: Function[ 4 ]: Type: Convolution Name: SqueezeNet/Convolution
Executor [0]: Function[ 5 ]: Type: ReLU Name: SqueezeNet/ReLU
Executor [0]: Function[ 6 ]: Type: MaxPooling Name: SqueezeNet/MaxPooling
SNIP...
Executor [0]: Function[ 63 ]: Type: ReLU Name: SqueezeNet/FireModule_8/Expand1x1ReLU
Executor [0]: Function[ 64 ]: Type: Concatenate Name: SqueezeNet/FireModule_8/Concatenate
Executor [0]: Function[ 65 ]: Type: Dropout Name: SqueezeNet/Dropout
Executor [0]: Function[ 66 ]: Type: Convolution Name: SqueezeNet/Convolution_2
Executor [0]: Function[ 67 ]: Type: ReLU Name: SqueezeNet/ReLU_2
Executor [0]: Function[ 68 ]: Type: AveragePooling Name: SqueezeNet/AveragePooling
Executor [0]: Function[ 69 ]: Type: Reshape Name: SqueezeNet/Reshape
Executor [0]: Function[ 70 ]: Type: Identity Name: y'
ImageAugmentation を除いたネットワークを取得したい場合、上記の出力結果によれば、ImageAugmentation は index 2 に配置されます。index 3 に分割した後、 ImageAugmentation を除いたネットワークを取得できます。 nnabla_cli 変換
で -E0 -S 3-
オプションを指定する必要があります。このコマンドで出力を XXX_S_E.nnp
という名前に変更します。 XXX は元の名前で、S は開始関数の index、E は終了関数の index です。
$ nnabla_cli convert -E0 -S 3- squeezenet11.files/SqueezeNet-1.1/*.{nntxt,h5} splitted.nnp
2018-08-27 15:20:21,950 [nnabla][INFO]: Initializing CPU extension...
Importing squeezenet11.files/SqueezeNet-1.1/net.nntxt
Importing squeezenet11.files/SqueezeNet-1.1/parameters.h5
Try to leave only executor[Executor].
Expanding Runtime.
Shrink 3 to 70.
Output to [splitted_3_70.nnp]
最終的に分割された出力として splitted_3_70.nnp
を取得できました。分割された NPP は nnabla_cli dump
で確認できます。
注意: Input shape は元のネットワークから変更されました。新しい input shape は開始関数の入力と同じです。
$ nnabla_cli dump splitted_3_70.nnp
2018-08-27 15:20:28,021 [nnabla][INFO]: Initializing CPU extension...
Importing splitted_3_70.nnp
Expanding Runtime.
Executor [0]: Executor
Executor [0]: (In) Data variable[0]: Name:SqueezeNet/MulScalar Shape:[-1, 3, 227, 227]
Executor [0]: (Out)Output variable[0]: Name:y' Shape:[-1, 1000]
以上で終了です。