既存のコードをUnity Sentis 1.5からUnity Sentis 1.6へ移行する

概要

Unity公式のディープラーニング推論フレームワークのSentis 1.6がリリースされました。Unity SentisはUnity 6と共にリリースされる予定であり、いよいよ正式リリースが近くなってきました。
Sentis 1.5からSentis 1.6へはAPIの破壊的な変更が含まれており、既存のコードをいくつか修正する必要があります。 この記事ではSentis 1.6の新機能をピックアップして紹介、主な既存のコードの書き換え事例を紹介していきます。

Unity Sentis 1.6

ChangeLog

Unity Sentis 1.6のWhatNewとChangeLogは以下のページで公開されいます。

docs.unity3d.com docs.unity3d.com

既存のコードの書き換え

Unity Sentis 1.5からUnity Sentis 1.6へのアップグレードガイドは以下で公開されています。 ここではUnity Sentis 1.5の既存のコードをUnity Sentis 1.6に書き換えるポイントをいくつか紹介します。 おそらく、Unity Sentisを利用している誰もが書き換えることになる部分をピックアップしました。

docs.unity3d.com

・IBackendのメソッドからkeepdim引数を削除

Unity Sentisでは1.4からIBackendクラスに定義されたメソッドでテンソルの演算を行うようになっています。 IBackendクラスのメソッドにはkeepdimという演算の入出力でテンソルの次元を保持するかどうか指定するbool型の引数が含まれるものがありました。 Unity Sentis 1.6からはkeepdim引数が削除され、出力テンソルの形状に沿うようになりました。
これはkeepdim引数に指定していたbool型を削除するだけなので簡単に書き換えて対応できます。

// Unity Sentis 1.5
var index_tensor = TensorInt.AllocNoData(new TensorShape(1));
backend.ArgMax(values_tensor, index_tensor , -1, keepdim:false, false);
// Unity Sentis 1.6
var index_tensor = TensorInt.AllocNoData(new TensorShape(1));
backend.ArgMax(values_tensor, index_tensor , -1, false);

・IBackend.Concat()からIBackend.SliceSet()への書き換え

Unity Sentis 1.5まではIBackend.Concat()メソッドで複数のテンソルを結合していました。
Unity Sentis 1.6ではIBackend.Concat()が削除され、代わりにIBackend.SliceSet()が追加されこちら利用するようになります。 なお、結合後のテンソルの形状を計算するTensorShape.Concat()は以前のまま利用できます。

// Unity Sentis 1.5
var concat_tensor = TensorFloat.AllocNoData(concat_shape);
backend.Concat(tensors_array, concat_tensor, axis);
// Unity Sentis 1.6
var concat_tensor = TensorFloat.AllocNoData(concat_shape);
var start = 0;
foreach (var tensor in tensors_array)
{
    backend.SliceSet(tensor, concat_tensor, axis, start, step:1);
    start += tensor.shape[axis];
}

・テンソルのダウンロード

Unity Sentis 1.5まではテンソルをダウンロードして値を読み取るためにTensor.CompleteOperationsAndDownload()を呼び出していました。 Unity Sentis 1.6からはこれをTensor.ReadbackAndClone()に置き換えるようになります。
メソッドの名前に「Clone」と付いていることからわかるように、テンソルのメモリの解放責任が呼び出した側にあることが明確になりました。 Tensor.ReadbackAndClone()を呼んでテンソルの値を読み取ったあとはTensor.Dispose()してメモリを解放しましょう。
また、Tensor.ReadbackAndCloneAsync()のように非同期でテンソルをダウンロードするメソッドが増えて簡単に扱えるようにもなりました。

// Unity Sentis 1.5
tensor.CompleteOperationsAndDownload();
var values = tensor.ToReadOnlySpan();
// Unity Sentis 1.6
tensor = tensor.ReadbackAndClone();
var values = tensor.ToReadOnlySpan();
tensor.Dispose();

まとめ

この記事ではUnity Sentis 1.6の新機能と既存のコードの書き換え事例を紹介しました。
Unity Sentisをベースにした画像認識パッケージであるHoloLab DNN Packagesは最新のUnity Sentis 1.6に対応済みです。 ぜひ、Unityアプリにディープラーニングによる画像認識を使った機能を組み込んで遊んでみてください。

blog.hololab.co.jp