TensorFlow Lite for iOS をビルドする

このドキュメントでは、TensorFlow Lite iOS ライブラリを独自にビルドする方法について説明します。通常、TensorFlow Lite iOS ライブラリをローカルでビルドする必要はありません。そのまま使用する場合は、TensorFlow Lite CocoaPods のビルド済みの安定版リリースまたはナイトリー リリースを使用するのが最も簡単な方法です。iOS プロジェクトでの使用方法について詳しくは、iOS クイックスタートをご覧ください。

ローカルでのビルド

場合によっては、TensorFlow Lite のローカルビルドを使用することをおすすめします。たとえば、TensorFlow Lite にローカルで変更を加えて iOS アプリでその変更をテストする場合や、Google が提供する動的フレームワークではなく静的フレームワークを使用する場合です。TensorFlow Lite 用のユニバーサル iOS フレームワークをローカルで作成するには、macOS マシンで Bazel を使用してビルドする必要があります。

Xcode をインストールする

まだインストールしていない場合は、Xcode 8 以降と、xcode-select を使用してツールをインストールする必要があります。

xcode-select --install

新規インストールの場合は、次のコマンドを使用して、すべてのユーザーの使用許諾契約に同意する必要があります。

sudo xcodebuild -license accept

Bazel をインストールする

Bazel は TensorFlow の主要なビルドシステムです。Bazel ウェブサイトの手順に沿って Bazel をインストールします。tensorflow リポジトリのルートにある configure.py ファイルで、_TF_MIN_BAZEL_VERSION_TF_MAX_BAZEL_VERSION のバージョンを選択してください。

WORKSPACE と .bazelrc の設定

TensorFlow チェックアウトのルート ディレクトリで ./configure スクリプトを実行し、iOS サポートを使用して TensorFlow をビルドするかどうかをスクリプトから尋ねられたら「はい」と答えます。

Bazel が iOS サポートで正しく構成されたら、次のコマンドを使用して TensorFlowLiteC フレームワークをビルドできます。

bazel build --config=ios_fat -c opt --cxxopt=--std=c++17 \
  //tensorflow/lite/ios:TensorFlowLiteC_framework

このコマンドにより、TensorFlow ルート ディレクトリの bazel-bin/tensorflow/lite/ios/ ディレクトリに TensorFlowLiteC_framework.zip ファイルが生成されます。デフォルトでは、生成されたフレームワークには armv7、arm64、x86_64 を含む「fat」バイナリが含まれています(i386 は含まれません)。--config=ios_fat を指定するときに使用されるビルドフラグの完全なリストについては、.bazelrc ファイルの iOS 構成セクションをご覧ください。

TensorFlowLiteC 静的フレームワークをビルドする

デフォルトでは、動的フレームワークは Cocoapods を介してのみ配布されます。静的フレームワークを使用する場合は、次のコマンドを使用して TensorFlowLiteC 静的フレームワークをビルドできます。

bazel build --config=ios_fat -c opt --cxxopt=--std=c++17 \
  //tensorflow/lite/ios:TensorFlowLiteC_static_framework

このコマンドにより、TensorFlow のルート ディレクトリの bazel-bin/tensorflow/lite/ios/ ディレクトリに TensorFlowLiteC_static_framework.zip という名前のファイルが生成されます。この静的フレームワークは、動的フレームワークとまったく同じように使用できます。

TFLite フレームワークを選択的に構築する

選択的ビルドを使用して、モデルセットのみをターゲットとする小規模なフレームワークを構築できます。これにより、モデルセット内の未使用のオペレーションがスキップされ、指定されたモデルセットの実行に必要なオペレーション カーネルのみが含まれます。コマンドは次のとおりです。

bash tensorflow/lite/ios/build_frameworks.sh \
  --input_models=model1.tflite,model2.tflite \
  --target_archs=x86_64,armv7,arm64

上記のコマンドは、TensorFlow Lite の組み込み演算とカスタム演算用の静的フレームワーク bazel-bin/tensorflow/lite/ios/tmp/TensorFlowLiteC_framework.zip を生成します。また、モデルに Select TensorFlow 演算が含まれている場合は、必要に応じて静的フレームワーク bazel-bin/tensorflow/lite/ios/tmp/TensorFlowLiteSelectTfOps_framework.zip を生成します。--target_archs フラグを使用してデプロイ アーキテクチャを指定できます。

独自のアプリケーションで使用する

CocoaPods デベロッパー

TensorFlow Lite には 3 つの CocoaPods があります。

  • TensorFlowLiteSwift: TensorFlow Lite 用の Swift API を提供します。
  • TensorFlowLiteObjC: TensorFlow Lite 用の Objective-C API を提供します。
  • TensorFlowLiteC: 共通のベース Pod。TensorFlow Lite コア ランタイムを埋め込み、上記の 2 つの Pod で使用されるベース C API を公開します。ユーザーが直接使用するためのものではありません。

デベロッパーは、アプリの作成言語に基づいて TensorFlowLiteSwift Pod または TensorFlowLiteObjC Pod のいずれかを選択する必要がありますが、両方は選択できません。TensorFlow Lite のローカルビルドを使用する正確な手順は、ビルドする部分によって異なります。

ローカルの Swift API または Objective-C API を使用する

CocoaPods を使用していて、TensorFlow Lite の Swift API または Objective-C API のローカルでの変更のみをテストする場合は、次の手順を行います。

  1. tensorflow チェックアウトで Swift API または Objective-C API に変更を加えます。

  2. TensorFlowLite(Swift|ObjC).podspec ファイルを開き、次の行を更新します。
    s.dependency 'TensorFlowLiteC', "#{s.version}"
    次のように更新します。
    s.dependency 'TensorFlowLiteC', "~> 0.0.1-nightly"
    これは、Swift または Objective-C API を、安定バージョンではなく、毎晩午前 1 時から 4 時(太平洋時間)の間にビルドされる TensorFlowLiteC API の最新のナイトリー バージョンに対してビルドできるようにするためです。これは、ローカルの tensorflow チェックアウトと比較して古くなっている可能性があります。または、独自のバージョンの TensorFlowLiteC を公開して、そのバージョンを使用することもできます(以下のローカル TensorFlow Lite コアの使用セクションをご覧ください)。

  3. iOS プロジェクトの Podfile で、tensorflow ルート ディレクトリのローカルパスを指すように、次のように依存関係を変更します。
    Swift の場合:
    pod 'TensorFlowLiteSwift', :path => '<your_tensorflow_root_dir>'
    Objective-C の場合:
    pod 'TensorFlowLiteObjC', :path => '<your_tensorflow_root_dir>'

  4. iOS プロジェクトのルート ディレクトリから Pod のインストールを更新します。
    $ pod update

  5. 生成されたワークスペース(<project>.xcworkspace)を再度開き、Xcode 内でアプリを再ビルドします。

ローカル TensorFlow Lite コアの使用

限定公開の CocoaPods 仕様リポジトリを設定し、カスタム TensorFlowLiteC フレームワークを限定公開リポジトリに公開できます。この podspec ファイルをコピーして、いくつかの値を変更できます。

  ...
  s.version      = <your_desired_version_tag>
  ...
  # Note the `///`, two from the `file://` and one from the `/path`.
  s.source       = { :http => "file:///path/to/TensorFlowLiteC_framework.zip" }
  ...
  s.vendored_frameworks = 'TensorFlowLiteC.framework'
  ...

独自の TensorFlowLiteC.podspec ファイルを作成したら、限定公開の CocoaPods の使用手順に沿って独自のプロジェクトで使用できます。カスタムの TensorFlowLiteC Pod を指すように TensorFlowLite(Swift|ObjC).podspec を変更し、アプリ プロジェクトで Swift または Objective-C Pod を使用することもできます。

Bazel デベロッパー

Bazel をメインのビルドツールとして使用する場合は、BUILD ファイルで TensorFlowLite 依存関係をターゲットに追加します。

Swift の場合:

swift_library(
  deps = [
      "//tensorflow/lite/swift:TensorFlowLite",
  ],
)

Objective-C の場合:

objc_library(
  deps = [
      "//tensorflow/lite/objc:TensorFlowLite",
  ],
)

アプリ プロジェクトをビルドすると、TensorFlow Lite ライブラリへの変更がすべて取得され、アプリに組み込まれます。

Xcode プロジェクトの設定を直接変更する

TensorFlow Lite の依存関係をプロジェクトに追加するには、CocoaPods または Bazel を使用することを強くおすすめします。それでも TensorFlowLiteC フレームワークを手動で追加する場合は、TensorFlowLiteC フレームワークを埋め込みフレームワークとしてアプリ プロジェクトに追加する必要があります。上記のビルドで生成された TensorFlowLiteC_framework.zip を解凍して、TensorFlowLiteC.framework ディレクトリを取得します。このディレクトリは、Xcode が認識できる実際のフレームワークです。

TensorFlowLiteC.framework を準備したら、まず、それを埋め込みバイナリとしてアプリのターゲットに追加する必要があります。そのための正確なプロジェクト設定セクションは、Xcode のバージョンによって異なる場合があります。

  • Xcode 11: アプリ ターゲットのプロジェクト エディタの [General] タブに移動し、[Frameworks, Libraries, and Embedded Content] セクションに TensorFlowLiteC.framework を追加します。
  • Xcode 10 以下: アプリ ターゲットのプロジェクト エディタの [General] タブに移動し、[Embedded Binaries] に TensorFlowLiteC.framework を追加します。また、[リンクされたフレームワークとライブラリ] セクションにフレームワークが自動的に追加されます。

フレームワークを埋め込みバイナリとして追加すると、Xcode は [Build Settings] タブの [Framework Search Paths] エントリも更新し、フレームワークの親ディレクトリが含まれるようになります。この処理が自動的に行われない場合は、TensorFlowLiteC.framework ディレクトリの親ディレクトリを手動で追加する必要があります。

この 2 つの設定が完了すると、TensorFlowLiteC.framework/Headers ディレクトリのヘッダー ファイルで定義された TensorFlow Lite の C API をインポートして呼び出すことができます。