このページは Cloud Translation API によって翻訳されました。
Switch to English

TensorFlow 2のTFハブからのSavedModels

TensorFlow 2SavedModel形式は、TensorFlow Hubで事前トレーニング済みモデルとモデルピースを共有するための推奨方法です。古いTF1ハブ形式を置き換え、新しいAPIセットが付属しています。

このページでは、低レベルのhub.load() APIとそのhub.KerasLayerラッパーを使用してTensorFlow 2プログラムでTF2 SavedModelsを再利用する方法について説明します。 (典型的には、 hub.KerasLayer他と組み合わされるtf.keras.layers Kerasモデルまたは構築するmodel_fn TF2推定のを。)これらのAPIはまた、制限内で、TF1ハブ形式の従来のモデルをロード見ることができる互換性ガイド

TensorFlow 1のユーザーは、TF 1.15に更新してから、同じAPIを使用できます。古いバージョンのTF1は機能しません。

TF HubからSavedModelsを使用する

KerasでのSavedModelの使用

Kerasは Keras Layerオブジェクトを構成することにより、深い学習モデルを構築するためのTensorFlowの高レベルAPIです。 tensorflow_hubライブラリは、クラスhub.KerasLayerを提供します。このクラスは、 hub.KerasLayerのURL(またはファイルシステムパス)で初期化され、事前トレーニングされた重みを含むSavedModelからの計算を提供します。

以下は、事前トレーニング済みのテキスト埋め込みの使用例です。

import tensorflow as tf
import tensorflow_hub as hub

hub_url = "https://tfhub.dev/google/tf2-preview/nnlm-en-dim128/1"
embed = hub.KerasLayer(hub_url)
embeddings = embed(["A long sentence.", "single-word", "http://example.com"])
print(embeddings.shape, embeddings.dtype)

これから、通常のKerasの方法でテキスト分類子を構築できます。

model = tf.keras.Sequential([
    embed,
    tf.keras.layers.Dense(16, activation="relu"),
    tf.keras.layers.Dense(1, activation="sigmoid"),
])

テキスト分類コラボは、そのような分類子をトレーニングして評価する方法の完全な例です。

hub.KerasLayerのモデルの重みは、 hub.KerasLayerではhub.KerasLayerに設定されています。これを変更する方法については、以下の微調整に関するセクションを参照してください。 Kerasの通常のように、重みは同じレイヤーオブジェクトのすべてのアプリケーション間で共有されます。

EstimatorでのSavedModelの使用

TensorFlowさんのユーザー見積もりの分散訓練のためのAPIは、彼らの書くことによってTFハブからSavedModelsを使用することができますmodel_fnするという点でhub.KerasLayer他の間でtf.keras.layers

舞台裏:SavedModelのダウンロードとキャッシュ

TensorFlow Hub(またはそのホスティングプロトコルを実装する他のHTTPSサーバー)からSavedModelを使用すると、ローカルファイルシステムがまだ存在しない場合は、ダウンロードして解凍します。環境変数TFHUB_CACHE_DIRを設定して、ダウンロードされた圧縮されていないSavedModelをキャッシュするためのデフォルトの一時的な場所を上書きできます。詳細については、 キャッシュを参照してください。

低レベルのTensorFlowでSavedModelを使用する

関数hub.load(handle)はSavedModelをダウンロードして解凍し( handleがすでにファイルシステムパスでない場合)、TensorFlowの組み込み関数tf.saved_model.load()を使用してロードした結果を返します。したがって、 hub.load()は有効なSavedModelを処理できます(TF1の以前のhub.Moduleとは異なります)。

高度なトピック:ロード後にSavedModelに期待すること

SavedModelの内容に応じて、 obj = hub.load(...)の結果はさまざまな方法で呼び出すことができます(TensorFlowのSavedModelガイドでより詳細に説明されています)。

  • SavedModelのサービス署名(存在する場合)は具象関数のディクショナリとして表され、 tensors_out = obj.signatures["serving_default"](**tensors_in)ようにtensors_out = obj.signatures["serving_default"](**tensors_in)ことができます。テンソルのディクショナリは、それぞれの入力と出力によってキー付けされます名前、および署名の形状とdtype制約に従います。

  • 保存されたオブジェクト(存在する場合)の@tf.function -decoratedメソッドは、保存前にtf.functionがトレースされていたTensor引数と非Tensor引数のすべての組み合わせによって呼び出すことができるtf.functionオブジェクトとして復元されます。特に、適切なトレースを備えたobj.__call__メソッドがある場合、 obj自体をPython関数のように呼び出すことができます。簡単な例は、 output_tensor = obj(input_tensor, training=False)ます。

これにより、SavedModelsが実装できるインターフェースに大きな自由が与えられます。 objReusable SavedModelsインターフェースは、 hub.KerasLayerなどのアダプターを含むクライアントコードがSavedModelの使用方法を認識できるようにする規則を確立します。

一部のSavedModelsは、その規則に準拠していない場合があり、特に大きなモデルでの再利用を意図していないモデル全体が提供され、サービス署名を提供するだけです。

SavedModelでのトレーニング可能な変数は、トレーニング可能として再ロードされ、そしてtf.GradientTape 、デフォルトではそれらを見るでしょう。いくつかの警告については、以下の微調整に関するセクションを参照し、初心者のためにこれを回避することを検討してください。微調整したい場合でも、 obj.trainable_variablesが元々トレーニング可能な変数のサブセットのみを再obj.trainable_variablesするようにアドバイスしているかどうかを確認したい場合があります。

TFハブのSavedModelの作成

概観

SavedModelは、トレーニング済みモデルまたはモデルピース用のTensorFlowの標準シリアル化形式です。モデルのトレーニング済みの重みと正確なTensorFlow演算を保存して、計算を実行します。それを作成したコードとは独立して使用できます。特に、TensorFlowの操作は共通の基本言語であるため、Kerasなどのさまざまな高レベルのモデル構築APIで再利用できます。

Kerasからの保存

TensorFlow 2以降、 tf.keras.Model.save()およびtf.keras.models.save_model()デフォルトはSavedModel形式(HDF5ではない)です。結果のSavedModelsは、他の高レベルAPIが利用可能になったときに、 hub.load()hub.KerasLayerなどのアダプターで使用できます。

完全なKerasモデルを共有するには、 include_optimizer=False保存するだけです。

Kerasモデルの一部を共有するには、その一部をモデル自体にしてから保存します。最初からそのようなコードをレイアウトできます。

piece_to_share = tf.keras.Model(...)
full_model = tf.keras.Sequential([piece_to_share, ...])
full_model.fit(...)
piece_to_share.save(...)

...または部分を切り取って、事後に共有します(完全なモデルのレイヤーと一致する場合)。

full_model = tf.keras.Model(...)
sharing_input = full_model.get_layer(...).get_output_at(0)
sharing_output = full_model.get_layer(...).get_output_at(0)
piece_to_share = tf.keras.Model(sharing_input, sharing_output)
piece_to_share.save(..., include_optimizer=False)

GitHub上のTensorFlowモデルは、BERTの前者のアプローチ( nlp / bert / bert_models.pyおよびnlp / bert / export_tfhub.pyを参照core_modelpretrain_model分割に注意)と、 pretrain_modelの後者のアプローチ( vision / image_classification / tfhub_exportを参照)を使用します.py )。

低レベルのTensorFlowからの保存

これには、TensorFlowのSavedModel Guideに精通している必要があります。

提供するシグネチャ以上のものを提供する場合は、 Reusable SavedModelインターフェースを実装する必要があります 。概念的には、これは次のようになります

class MyMulModel(tf.train.Checkpoint):
  def __init__(self, v_init):
    super(MyMulModel, self).__init__()
    self.v = tf.Variable(v_init)
    self.variables = [self.v]
    self.trainable_variables = [self.v]
    self.regularization_losses = [
        tf.function(input_signature=[])(lambda: 0.001 * self.v**2),
    ]

  @tf.function(input_signature=[tf.TensorSpec(shape=None, dtype=tf.float32)])
  def __call__(self, inputs):
    return tf.multiply(inputs, self.v)

tf.saved_model.save(MyMulModel(2.0), "/tmp/my_mul")

layer = hub.KerasLayer("/tmp/my_mul")
print(layer([10., 20.]))  # [20., 40.]
layer.trainable = True
print(layer.trainable_weights)  # [2.]
print(layer.losses)  # 0.004

tensorflow / examples / saved_model / integration_tests /にあるコードには、特に大きな例が含まれています。 export_mnist.pyuse_mnist.pyペア。

微調整

インポートされたSavedModelのすでにトレーニングされた変数を、その周りのモデルの変数とともにトレーニングすることを、SavedModelの微調整と呼びます。これにより、品質が向上しますが、トレーニングの負荷が高くなります(時間がかかる可能性があり、オプティマイザーとそのハイパーパラメーターに大きく依存し、過剰適合のリスクが高くなり、特にCNNなどのデータセットの拡張が必要になります)。 SavedModelコンシューマーは、適切なトレーニング体制を確立した後で、SavedModelパブリッシャーが推奨する場合にのみ、微調整を検討することをお勧めします。

微調整により、トレーニングされる「連続的な」モデルパラメーターが変更されます。テキスト入力のトークン化や埋め込み行列の対応するエントリへのトークンのマッピングなど、ハードコードされた変換は変更されません。

SavedModelコンシューマー向け

hub.KerasLayer作成hub.KerasLayerような

layer = hub.KerasLayer(..., trainable=True)

レイヤーによって読み込まれたSavedModelの微調整を有効にします。これは、SavedModelで宣言されたトレーニング可能な重みと重みレギュラライザーをKerasモデルに追加し、トレーニングモード(ドロップアウトなど)でSavedModelの計算を実行します。

画像分類コラボには、オプションの微調整を伴うエンドツーエンドの例が含まれています。

微調整結果の再エクスポート

上級ユーザーは、微調整の結果を、最初に読み込まれたモデルの代わりに使用できるSavedModelに保存したい場合があります。これは次のようなコードで行うことができます

loaded_obj = hub.load("https://tfhub.dev/...")
hub_layer = hub.KerasLayer(loaded_obj, trainable=True, ...)

model = keras.Sequential([..., hub_layer, ...])
model.compile(...)
model.fit(...)

export_module_dir = os.path.join(os.getcwd(), "finetuned_model_export")
tf.saved_model.save(loaded_obj, export_module_dir)

SavedModel作成者向け

TensorFlow Hubで共有するためのSavedModelを作成するときは、コンシューマーがそれを微調整する必要があるかどうか、またその方法を事前に検討し、ドキュメントでガイダンスを提供します。

Kerasモデルから保存すると、微調整作業のすべてのメカニズムが実行されます(重みの正規化による損失の保存、トレーニング可能な変数の宣言、 training=Truetraining=False両方の__call__トレースなど)。

勾配流とうまく機能するモデルインターフェイスを選択します。たとえば、softmax確率やトップk予測の代わりに出力ロジットを使用します。

モデルでドロップアウト、バッチ正規化、またはハイパーパラメーターを含む同様のトレーニング手法を使用する場合は、ハイパーパラメーターを、予想される多くのターゲットの問題とバッチサイズで意味のある値に設定します。 (これを書いている時点では、 Kerasから保存しても、消費者がそれらを調整するのは簡単ではありませんが、いくつかの大まかな回避策については、 tensorflow / examples / saved_model / integration_tests / export_mnist_cnn.py参照してください。)

個々のレイヤーの重み正則化機能は(正則化強度係数とともに)保存されますが、オプティマイザー内からの重み正則化( tf.keras.optimizers.Ftrl.l1_regularization_strength=...) )は失われます。 SavedModelの消費者に適宜アドバイスしてください。