Ta strona została przetłumaczona przez Cloud Translation API.
Switch to English

Migrować kod TensorFlow 1 do 2 TensorFlow

Zobacz na TensorFlow.org Uruchom Google Colab Zobacz źródło na GitHub Pobierz notebook

Ten dokument dla użytkowników niskiego poziomu TensorFlow API. Jeśli korzystasz z wysokiego poziomu API ( tf.keras ) nie mogą być niewielkie lub żadne działania trzeba podjąć, aby kod pełni TensorFlow 2.0 kompatybilne:

Jest jeszcze możliwość, aby uruchomić kod 1.x, niemodyfikowana ( z wyjątkiem contrib ), w TensorFlow 2.0:

 import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
 

Jednak to nie pozwala skorzystać z wielu ulepszeń wprowadzonych w TensorFlow 2.0. Ten poradnik pomoże Ci uaktualnić swój kod, dzięki czemu jest prostsze, bardziej wydajnych i łatwiejsze w utrzymaniu.

Automatyczny skrypt konwersji

Pierwszym krokiem, przed przystąpieniem do wdrożenia zmian opisanych w niniejszym dokumencie, to spróbuj uruchomić skrypt aktualizacyjny .

Będzie to zrobić wstępną przepustkę na uaktualnienie kodu do TensorFlow 2.0. Ale to nie może mieć swój kod idiomatyczne do 2,0. Kod może nadal wykorzystywać tf.compat.v1 końcowych do dostępu zastępcze, sesje, zbiorów i innych funkcjonalności 1.x stylu.

Najwyższego poziomu zmiany behawioralne

Jeśli Twój kod działa w TensorFlow 2,0 użyciu tf.compat.v1.disable_v2_behavior() , nadal istnieją globalne zmiany behawioralne może trzeba będzie rozwiązać. Główne zmiany to:

  • Marzą wykonanie, v1.enable_eager_execution() : Każdy kod, który domyślnie używa tf.Graph zawiedzie. Pamiętaj, aby zawinąć ten kod w sposób with tf.Graph().as_default() kontekst.

  • Zmienne zasobu, v1.enable_resource_variables() : Niektóre programy mogą zależy od zachowań niedeterministycznym włączona zmiennych referencyjnych TF. Zmienne zasobów są zablokowane, gdy są zapisywane, a więc zapewnić bardziej intuicyjne gwarancje spójności.

    • To może zmienić zachowania w przypadkach krawędzi.
    • To może tworzyć dodatkowe kopie i mogą mieć wyższe zużycie pamięci.
    • To może być wyłączone przez przepuszczenie use_resource=False do tf.Variable konstruktora.
  • Tensor kształty v1.enable_v2_tensorshape() : TF 2,0 ułatwia zachowanie kształtu tensor. Zamiast t.shape[0].value można powiedzieć t.shape[0] . Zmiany te powinny być małe, a to ma sens, aby rozwiązać je od razu. Zobacz TensorShape przykłady.

  • Kontroli przepływu v1.enable_control_flow_v2() : Realizacja sterowania przepływem 2,0 TF uproszczone, a więc wytwarza różne przedstawienia wykresu. Proszę błędy plików do żadnych problemów.

Wykorzystaj kod 2,0-native

Ten przewodnik poprowadzi przez kilka przykładów konwersji TensorFlow kod 1.x do TensorFlow 2.0. Zmiany te pozwolą swój kod skorzystać z optymalizacji wydajności i uproszczone API.

W każdym przypadku, wzorzec jest:

1. Wymień v1.Session.run połączeń

Każdy v1.Session.run wezwanie powinna zostać zastąpiona przez funkcję Pythona.

  • W feed_dict i v1.placeholder s stają się argumenty funkcji.
  • W fetches stała wartość powrotu z funkcji.
  • Podczas konwersji chętny wykonanie umożliwia łatwe debugowanie przy użyciu standardowych narzędzi takich jak Python pdb .

Następnie dodać tf.function dekorator, aby go uruchomić efektywnie na wykresie. Zobacz Autograph przewodnik dla bardziej na jak to działa.

Należy pamiętać, że:

  • W przeciwieństwie v1.Session.run tf.function ma stały podpis zwrotny i zawsze zwraca wszystkie wyjścia. Jeśli powoduje to problemy z wydajnością, należy utworzyć dwie odrębne funkcje.

  • Nie ma potrzeby, przez tf.control_dependencies lub podobnych operacji: a tf.function zachowuje się tak, jakby były uruchamiane w kolejności pisemnej. tf.Variable zadania i tf.assert s, na przykład, są wykonywane automatycznie.

2. Użyj Python obiektów do zmiennych i strat toru

Wszystko oparte na śledzenie nazwa zmiennej jest zdecydowanie odradzane w TF 2.0. Zastosowanie Python sprzeciwia się śledzić zmienne.

Zastosowanie tf.Variable zamiast v1.get_variable .

Każdy v1.variable_scope powinny zostać przekształcone w obiekt Pythona. Zazwyczaj będzie to jedno z:

Jeśli trzeba zbiorczych wykazów zmiennych (jak tf.Graph.get_collection(tf.GraphKeys.VARIABLES) ), użyj .variables i .trainable_variables atrybutów Layer i Model obiektów.

Te Layer i Model klas wdrożyć kilka innych właściwości, które usuwają potrzebę światowych kolekcjach. Ich .losses nieruchomość może być zamiennikiem pomocą tf.GraphKeys.LOSSES kolekcję.

Zobacz Keras prowadnice dla szczegółów.

3. Uaktualnij pętle treningowe

Użyj najwyższy poziom API, który pracuje dla przypadku użycia. Wolę tf.keras.Model.fit na budowanie własnych pętle treningowe.

Te funkcje wysokiego szczebla zarządzania dużo szczegółów niskopoziomowych, które mogą być łatwo przegapić jeśli napiszesz swoją pętlę treningową. Na przykład, automatycznie zbierać straty regularyzacji i ustaw training=True argumentu przy wywołaniu model.

4. Uaktualnij rurociągów dane wejściowe

Użyj tf.data zestawów danych do wprowadzania danych. Obiekty te są skuteczne, wyraziste, a także integrację z tensorflow.

Mogą one być przekazywane bezpośrednio do tf.keras.Model.fit metody.

 model.fit(dataset, epochs=5)
 

Można je powtórzyć bezpośrednio nad standardowej Pythona:

 for example_batch, label_batch in dataset:
    break
 

5. migracji od compat.v1 symboli

tf.compat.v1 moduł zawiera kompletny TensorFlow 1.x API, z jego oryginalnych semantyki.

Skrypt aktualizacji TF2 przekonwertuje symboli do ich odpowiedników 2.0 jeśli taka konwersja jest bezpieczna, to znaczy, jeśli można ustalić, że zachowanie wersji 2.0 jest dokładnie równoważne (na przykład, to zmień v1.arg_max do tf.argmax , ponieważ są to te same funkcje).

Po skrypt aktualizacji odbywa się z kawałkiem kodu, to prawdopodobnie istnieje wiele wzmianek o compat.v1 . Warto wybrać się za pomocą kodu i przekształcenie ich ręcznie do równowartości 2,0 (należy wspomnieć w dzienniku jeśli istnieje).

Konwersja modeli

Ustawiać

 import tensorflow as tf


import tensorflow_datasets as tfds
 

Zmienne niskim poziomie i wykonanie operatora

Przykłady zastosowania niskiego poziomu API obejmują:

przed konwersją

Oto, co te wzory mogą wyglądać w kodzie za pomocą TensorFlow 1.x.

 in_a = tf.placeholder(dtype=tf.float32, shape=(2))
in_b = tf.placeholder(dtype=tf.float32, shape=(2))

def forward(x):
  with tf.variable_scope("matmul", reuse=tf.AUTO_REUSE):
    W = tf.get_variable("W", initializer=tf.ones(shape=(2,2)),
                        regularizer=tf.contrib.layers.l2_regularizer(0.04))
    b = tf.get_variable("b", initializer=tf.zeros(shape=(2)))
    return W * x + b

out_a = forward(in_a)
out_b = forward(in_b)

reg_loss=tf.losses.get_regularization_loss(scope="matmul")

with tf.Session() as sess:
  sess.run(tf.global_variables_initializer())
  outs = sess.run([out_a, out_b, reg_loss],
                feed_dict={in_a: [1, 0], in_b: [0, 1]})

 

po konwersji

W kodzie przekształconego:

  • Zmienne lokalne są obiekty Pythona.
  • forward funkcja nadal definiuje obliczenia.
  • Session.run połączenie zostanie zastąpiony przez wywołanie forward
  • Opcjonalny tf.function dekorator można dodać do wydajności.
  • W regularyzacji obliczane są ręcznie, bez odwoływania się do każdej kolekcji globalnej.
  • Brak sesje lub zastępcze.
 W = tf.Variable(tf.ones(shape=(2,2)), name="W")
b = tf.Variable(tf.zeros(shape=(2)), name="b")

@tf.function
def forward(x):
  return W * x + b

out_a = forward([1,0])
print(out_a)
 
tf.Tensor(
[[1. 0.]
 [1. 0.]], shape=(2, 2), dtype=float32)

 out_b = forward([0,1])

regularizer = tf.keras.regularizers.l2(0.04)
reg_loss=regularizer(W)
 

Modele oparte na tf.layers

v1.layers modułu jest użyty do umieszczenia warstwy-funkcje opierał na v1.variable_scope określenia zmiennych i ponownego wykorzystania.

przed konwersją

 def model(x, training, scope='model'):
  with tf.variable_scope(scope, reuse=tf.AUTO_REUSE):
    x = tf.layers.conv2d(x, 32, 3, activation=tf.nn.relu,
          kernel_regularizer=tf.contrib.layers.l2_regularizer(0.04))
    x = tf.layers.max_pooling2d(x, (2, 2), 1)
    x = tf.layers.flatten(x)
    x = tf.layers.dropout(x, 0.1, training=training)
    x = tf.layers.dense(x, 64, activation=tf.nn.relu)
    x = tf.layers.batch_normalization(x, training=training)
    x = tf.layers.dense(x, 10)
    return x

train_out = model(train_data, training=True)
test_out = model(test_data, training=False)
 

po konwersji

Większość argumentów pozostał taki sam. Ale zauważmy różnice:

  • training argument jest przekazywany do każdej warstwy w modelu, gdy skończy.
  • Pierwszy argument do oryginalnego model funkcji (wprowadzić x ) nie ma. To dlatego, że warstwy obiektów oddzielnym budynku model z wywołaniem model.

Należy również pamiętać, że:

  • Jesli uzywasz regularizers z inicjalizatorów z tf.contrib te mają więcej argumentów niż inne zmiany.
  • Kod nie pisze do zbiorów, a więc działa jak v1.losses.get_regularization_loss już nie powrócą te wartości, potencjalnie łamiąc swoje pętle treningowe.
 model = tf.keras.Sequential([
    tf.keras.layers.Conv2D(32, 3, activation='relu',
                           kernel_regularizer=tf.keras.regularizers.l2(0.04),
                           input_shape=(28, 28, 1)),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dropout(0.1),
    tf.keras.layers.Dense(64, activation='relu'),
    tf.keras.layers.BatchNormalization(),
    tf.keras.layers.Dense(10)
])

train_data = tf.ones(shape=(1, 28, 28, 1))
test_data = tf.ones(shape=(1, 28, 28, 1))
 
 train_out = model(train_data, training=True)
print(train_out)
 
tf.Tensor([[0. 0. 0. 0. 0. 0. 0. 0. 0. 0.]], shape=(1, 10), dtype=float32)

 test_out = model(test_data, training=False)
print(test_out)
 
tf.Tensor(
[[-0.11456077 -0.3126101   0.13154565 -0.50197905 -0.02416557  0.36460522
  -0.24887308 -0.37784547  0.05524942  0.01696768]], shape=(1, 10), dtype=float32)

 # Here are all the trainable variables.
len(model.trainable_variables)
 
8
 # Here is the regularization loss.
model.losses
 
[<tf.Tensor: shape=(), dtype=float32, numpy=0.077528305>]

Zmienne mieszane i v1.layers

Istniejący kod często mieszanki niższego poziomu TF 1.x zmienne i operacje z wyższego poziomu v1.layers .

przed konwersją

 def model(x, training, scope='model'):
  with tf.variable_scope(scope, reuse=tf.AUTO_REUSE):
    W = tf.get_variable(
      "W", dtype=tf.float32,
      initializer=tf.ones(shape=x.shape),
      regularizer=tf.contrib.layers.l2_regularizer(0.04),
      trainable=True)
    if training:
      x = x + W
    else:
      x = x + W * 0.5
    x = tf.layers.conv2d(x, 32, 3, activation=tf.nn.relu)
    x = tf.layers.max_pooling2d(x, (2, 2), 1)
    x = tf.layers.flatten(x)
    return x

train_out = model(train_data, training=True)
test_out = model(test_data, training=False)
 

po konwersji

W celu przekształcenia tego kodu zgodne ze schematem odwzorowywania warstwy do warstwy, jak w poprzednim przykładzie.

Ogólny wzór jest:

  • Zebrać parametrów warstwy w __init__ .
  • Budowanie zmienne w build .
  • Wykonać obliczenia w call i zwraca wynik.

v1.variable_scope jest zasadniczo warstwa własnych. Tak przerobić go jako tf.keras.layers.Layer . Zobacz przewodnik po szczegóły.

 # Create a custom layer for part of the model
class CustomLayer(tf.keras.layers.Layer):
  def __init__(self, *args, **kwargs):
    super(CustomLayer, self).__init__(*args, **kwargs)

  def build(self, input_shape):
    self.w = self.add_weight(
        shape=input_shape[1:],
        dtype=tf.float32,
        initializer=tf.keras.initializers.ones(),
        regularizer=tf.keras.regularizers.l2(0.02),
        trainable=True)

  # Call method will sometimes get used in graph mode,
  # training will get turned into a tensor
  @tf.function
  def call(self, inputs, training=None):
    if training:
      return inputs + self.w
    else:
      return inputs + self.w * 0.5
 
 custom_layer = CustomLayer()
print(custom_layer([1]).numpy())
print(custom_layer([1], training=True).numpy())
 
[1.5]
[2.]

 train_data = tf.ones(shape=(1, 28, 28, 1))
test_data = tf.ones(shape=(1, 28, 28, 1))

# Build the model including the custom layer
model = tf.keras.Sequential([
    CustomLayer(input_shape=(28, 28, 1)),
    tf.keras.layers.Conv2D(32, 3, activation='relu'),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
])

train_out = model(train_data, training=True)
test_out = model(test_data, training=False)

 

Niektóre rzeczy do uwaga:

  • Podklasy Keras modele i warstwy trzeba uruchomić w obu wykresach V1 (brak automatycznego zależnościami sterowania) oraz w trybie upragnieniem

    • Owiń call() w tf.function() , aby uzyskać autograf i automatycznych zależności sterujących
  • Nie zapomnij zaakceptować training argument do call .

    • Czasami jest to tf.Tensor
    • Czasami jest to logiczna Python.
  • Tworzenie modelu zmiennych w konstruktorze lub Model.build użyciu self.add_weight() .

    • W Model.build masz dostęp do kształtu wejściowego, dzięki czemu można tworzyć ciężary z pasującymi kształt.
    • Korzystanie tf.keras.layers.Layer.add_weight pozwala Keras zmiennym rozstawie i strat legalizacji.
  • Nie trzymaj tf.Tensors w swoich obiektach.

    • Mogą dostać tworzone zarówno w tf.function lub w kontekście chętny, a te tensory zachowują się inaczej.
    • Zastosowanie tf.Variable s do stanu, zawsze są użyteczne z obu kontekstach
    • tf.Tensors tylko dla wartości pośrednich.

Uwaga na Slim & contrib.layers

Duża ilość starszego kodu TensorFlow 1.x wykorzystuje Slim biblioteki, które zostało dostarczone wraz z TensorFlow 1.x jako tf.contrib.layers . Jako contrib modułu, to nie jest już dostępna w TensorFlow 2.0, nawet w tf.compat.v1 . Konwersja kodu przy użyciu Slim TF 2.0 jest bardziej zaangażowany niż konwersja repozytoriów, które używają v1.layers . W rzeczywistości może to sens do konwersji kodu Slim do v1.layers pierwszy, a następnie przekonwertować do Keras.

  • Usuwanie arg_scopes wszystkie argumenty muszą być jawne
  • Jeśli używasz ich podziału normalizer_fn i activation_fn do własnych warstw
  • Rozdzielenia warstw conv mapowane do jednego lub większej liczby różnych warstw Keras (odnoszącym się do głębokości, punktowo i oddzielnych warstw Keras)
  • Slim i v1.layers mają różne nazwy Arg wartości domyślnych
  • Niektóre argumenty mają różne skale
  • Jeśli używasz Slim wstępnie przeszkolony modele, wypróbować wcześniej traimed modele Keras jest od tf.keras.applications lub TF Hub „s TF2 SavedModels eksportowane z oryginalnego kodu Slim.

Niektóre tf.contrib warstwy nie może zostały przeniesione do rdzenia TensorFlow ale zamiast została przeniesiona do add-ons pakietu TF .

Trening

Istnieje wiele sposobów, aby dane paszowych do tf.keras modelu. Będą przyjmować generatory Python i tablice numpy jako wejście.

Zalecany sposób karmienia danych do modelu jest użycie tf.data pakiet, który zawiera zbiór wysokich klasach wydajności do manipulowania danymi.

Jeśli nadal używa tf.queue te są obecnie obsługiwane tylko w strukturach danych, a nie jak rurociągi wejściowych.

Korzystanie z zestawów danych

TensorFlow zestawów danych pakiet ( tfds ) zawiera narzędzia do wczytywania predefiniowanych zestawów danych jako tf.data.Dataset obiektów.

W tym przykładzie, załaduj MNISTdataset korzystając tfds :

 datasets, info = tfds.load(name='mnist', with_info=True, as_supervised=True)
mnist_train, mnist_test = datasets['train'], datasets['test']
 
Downloading and preparing dataset mnist/3.0.1 (download: 11.06 MiB, generated: 21.00 MiB, total: 32.06 MiB) to /home/kbuilder/tensorflow_datasets/mnist/3.0.1...

Warning:absl:Dataset mnist is hosted on GCS. It will automatically be downloaded to your
local data directory. If you'd instead prefer to read directly from our public
GCS bucket (recommended if you're running on GCP), you can instead pass
`try_gcs=True` to `tfds.load` or set `data_dir=gs://tfds-data/datasets`.


Dataset mnist downloaded and prepared to /home/kbuilder/tensorflow_datasets/mnist/3.0.1. Subsequent calls will reuse this data.

Następnie przygotować dane do szkolenia:

  • Re skalę każdego obrazu.
  • Przetasować kolejność przykładów.
  • Zbieraj partie zdjęć i etykiety.
 BUFFER_SIZE = 10 # Use a much larger value for real code.
BATCH_SIZE = 64
NUM_EPOCHS = 5


def scale(image, label):
  image = tf.cast(image, tf.float32)
  image /= 255

  return image, label
 

Aby utrzymać Krótki, przykładowy, wykończenia zestawu danych tylko do powrotu 5 porcji:

 train_data = mnist_train.map(scale).shuffle(BUFFER_SIZE).batch(BATCH_SIZE)
test_data = mnist_test.map(scale).batch(BATCH_SIZE)

STEPS_PER_EPOCH = 5

train_data = train_data.take(STEPS_PER_EPOCH)
test_data = test_data.take(STEPS_PER_EPOCH)
 
 image_batch, label_batch = next(iter(train_data))
 

pętle treningowe użycie Keras

Jeśli nie potrzebujesz niski poziom waszej kontroli procesu szkolenia, korzystając Keras wbudowanego w fit , evaluate i predict metody jest zalecane. Metody te zapewniają interfejs jednolitego trenowania modelu niezależnie od wykonania (sekwencyjne, funkcjonalny lub sub-klasyfikowane).

Zalety te metody obejmują:

  • Oni akceptują tablice numpy, generatory Pythona, tf.data.Datasets
  • Są one automatycznie zastosować straty uregulowanie i aktywacji.
  • Wspierają one tf.distribute szkolenia multi-device .
  • Wspierają one arbitralne callables jako straty i metryki.
  • Wspierają one wywołania zwrotne jak tf.keras.callbacks.TensorBoard i niestandardowe wywołania zwrotne.
  • Są wydajnych, automatycznie za pomocą wykresów TensorFlow.

Oto przykład szkolenia model używając Dataset . (Szczegółowe informacje na temat, jak to działa zobaczyć tutoriale ).

 model = tf.keras.Sequential([
    tf.keras.layers.Conv2D(32, 3, activation='relu',
                           kernel_regularizer=tf.keras.regularizers.l2(0.02),
                           input_shape=(28, 28, 1)),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dropout(0.1),
    tf.keras.layers.Dense(64, activation='relu'),
    tf.keras.layers.BatchNormalization(),
    tf.keras.layers.Dense(10)
])

# Model is the full model w/o custom layers
model.compile(optimizer='adam',
              loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True),
              metrics=['accuracy'])

model.fit(train_data, epochs=NUM_EPOCHS)
loss, acc = model.evaluate(test_data)

print("Loss {}, Accuracy {}".format(loss, acc))
 
Epoch 1/5
5/5 [==============================] - 0s 6ms/step - loss: 1.5323 - accuracy: 0.5063
Epoch 2/5
5/5 [==============================] - 0s 6ms/step - loss: 0.4105 - accuracy: 0.9219
Epoch 3/5
5/5 [==============================] - 0s 7ms/step - loss: 0.2495 - accuracy: 0.9531
Epoch 4/5
5/5 [==============================] - 0s 6ms/step - loss: 0.1806 - accuracy: 0.9875
Epoch 5/5
5/5 [==============================] - 0s 6ms/step - loss: 0.1416 - accuracy: 0.9937
5/5 [==============================] - 0s 4ms/step - loss: 1.5655 - accuracy: 0.6469
Loss 1.565544605255127, Accuracy 0.6468750238418579

Napisz własną pętlę

Jeśli krok szkolenie modelki Keras za roboty dla ciebie, ale trzeba więcej poza kontrolą, że krok, należy rozważyć użycie tf.keras.Model.train_on_batch sposób, w swoim własnym pętli danych iteracji.

Pamiętaj: Wiele rzeczy może być realizowany jako tf.keras.callbacks.Callback .

Sposób ten posiada wiele zalet tych sposobów opisanych w poprzedniej sekcji, lecz zapewnia lepszą kontrolę w pętli zewnętrznej.

Można również użyć tf.keras.Model.test_on_batch lub tf.keras.Model.evaluate do wykonywania wyboru podczas treningu.

Aby kontynuować szkolenie powyższy model:

 # Model is the full model w/o custom layers
model.compile(optimizer='adam',
              loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True),
              metrics=['accuracy'])

for epoch in range(NUM_EPOCHS):
  #Reset the metric accumulators
  model.reset_metrics()

  for image_batch, label_batch in train_data:
    result = model.train_on_batch(image_batch, label_batch)
    metrics_names = model.metrics_names
    print("train: ",
          "{}: {:.3f}".format(metrics_names[0], result[0]),
          "{}: {:.3f}".format(metrics_names[1], result[1]))
  for image_batch, label_batch in test_data:
    result = model.test_on_batch(image_batch, label_batch,
                                 # return accumulated metrics
                                 reset_metrics=False)
  metrics_names = model.metrics_names
  print("\neval: ",
        "{}: {:.3f}".format(metrics_names[0], result[0]),
        "{}: {:.3f}".format(metrics_names[1], result[1]))
 
train:  loss: 0.122 accuracy: 0.984
train:  loss: 0.133 accuracy: 0.984
train:  loss: 0.164 accuracy: 0.969
train:  loss: 0.167 accuracy: 0.969
train:  loss: 0.161 accuracy: 0.984

eval:  loss: 1.583 accuracy: 0.669
train:  loss: 0.074 accuracy: 1.000
train:  loss: 0.090 accuracy: 1.000
train:  loss: 0.089 accuracy: 1.000
train:  loss: 0.095 accuracy: 1.000
train:  loss: 0.090 accuracy: 1.000

eval:  loss: 1.567 accuracy: 0.747
train:  loss: 0.065 accuracy: 1.000
train:  loss: 0.068 accuracy: 1.000
train:  loss: 0.056 accuracy: 1.000
train:  loss: 0.069 accuracy: 1.000
train:  loss: 0.067 accuracy: 1.000

eval:  loss: 1.545 accuracy: 0.772
train:  loss: 0.053 accuracy: 1.000
train:  loss: 0.063 accuracy: 0.984
train:  loss: 0.050 accuracy: 1.000
train:  loss: 0.051 accuracy: 1.000
train:  loss: 0.049 accuracy: 1.000

eval:  loss: 1.520 accuracy: 0.778
train:  loss: 0.049 accuracy: 1.000
train:  loss: 0.046 accuracy: 1.000
train:  loss: 0.044 accuracy: 1.000
train:  loss: 0.045 accuracy: 1.000
train:  loss: 0.044 accuracy: 1.000

eval:  loss: 1.494 accuracy: 0.791

Dostosuj etap treningowy

Jeśli potrzebujesz większej elastyczności i kontroli, można mieć go poprzez wdrożenie własnego pętlę treningową. Istnieją trzy etapy:

  1. Iteracyjne nad generatorem Python lub tf.data.Dataset dostać partii przykładów.
  2. Użyj tf.GradientTape zebrać gradientów.
  3. Użyj jednego z tf.keras.optimizers zastosować aktualizacje wagi do zmiennych modelu.

Zapamiętaj:

  • Zawsze zawierać training argument na call metody podklasy warstw i modeli.
  • Upewnij się, aby zadzwonić do modelu ze training zestaw argumentów poprawnie.
  • W zależności od sposobu użytkowania, zmienne model nie może istnieć aż model jest prowadzony na partii danych.
  • Trzeba ręcznie obsługiwać takie rzeczy jak straty legalizacji dla modelu.

Uwaga uproszczeń w stosunku do V1:

  • Nie ma potrzeby, aby uruchomić zmienne inicjatorów. Zmienne są inicjowane na stworzeniu.
  • Nie ma potrzeby dodawania ręcznych zależności sterujących. Nawet w tf.function operacje działają jak w trybie chętny.
 model = tf.keras.Sequential([
    tf.keras.layers.Conv2D(32, 3, activation='relu',
                           kernel_regularizer=tf.keras.regularizers.l2(0.02),
                           input_shape=(28, 28, 1)),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dropout(0.1),
    tf.keras.layers.Dense(64, activation='relu'),
    tf.keras.layers.BatchNormalization(),
    tf.keras.layers.Dense(10)
])

optimizer = tf.keras.optimizers.Adam(0.001)
loss_fn = tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True)

@tf.function
def train_step(inputs, labels):
  with tf.GradientTape() as tape:
    predictions = model(inputs, training=True)
    regularization_loss=tf.math.add_n(model.losses)
    pred_loss=loss_fn(labels, predictions)
    total_loss=pred_loss + regularization_loss

  gradients = tape.gradient(total_loss, model.trainable_variables)
  optimizer.apply_gradients(zip(gradients, model.trainable_variables))

for epoch in range(NUM_EPOCHS):
  for inputs, labels in train_data:
    train_step(inputs, labels)
  print("Finished epoch", epoch)

 
Finished epoch 0
Finished epoch 1
Finished epoch 2
Finished epoch 3
Finished epoch 4

Metryki i straty w nowym stylu

W TensorFlow 2.0, metryki i straty są obiektami. Działają one zarówno ochoczo iw tf.function s.

Obiekt strata jest wymagalne, a oczekuje (y_true, y_pred) jako argumenty:

 cce = tf.keras.losses.CategoricalCrossentropy(from_logits=True)
cce([[1, 0]], [[-1.0,3.0]]).numpy()
 
4.01815

Metryka obiekt ma następujące metody:

Sam obiekt jest wymagalne. Wywołanie aktualizuje stan z nowymi obserwacjami, jak z update_state i zwraca nowy wynik metryką.

Nie trzeba ręcznie zainicjować metryki zmienne, a ponieważ TensorFlow 2.0 posiada automatyczny zależności kontrolnych, nie trzeba się martwić o tych, albo.

Poniższy kod wykorzystuje metrycznych śledzić średniej straty obserwowanego w pętli niestandardowe szkolenia.

 # Create the metrics
loss_metric = tf.keras.metrics.Mean(name='train_loss')
accuracy_metric = tf.keras.metrics.SparseCategoricalAccuracy(name='train_accuracy')

@tf.function
def train_step(inputs, labels):
  with tf.GradientTape() as tape:
    predictions = model(inputs, training=True)
    regularization_loss=tf.math.add_n(model.losses)
    pred_loss=loss_fn(labels, predictions)
    total_loss=pred_loss + regularization_loss

  gradients = tape.gradient(total_loss, model.trainable_variables)
  optimizer.apply_gradients(zip(gradients, model.trainable_variables))
  # Update the metrics
  loss_metric.update_state(total_loss)
  accuracy_metric.update_state(labels, predictions)


for epoch in range(NUM_EPOCHS):
  # Reset the metrics
  loss_metric.reset_states()
  accuracy_metric.reset_states()

  for inputs, labels in train_data:
    train_step(inputs, labels)
  # Get the metric results
  mean_loss=loss_metric.result()
  mean_accuracy = accuracy_metric.result()

  print('Epoch: ', epoch)
  print('  loss:     {:.3f}'.format(mean_loss))
  print('  accuracy: {:.3f}'.format(mean_accuracy))

 
Epoch:  0
  loss:     0.175
  accuracy: 0.994
Epoch:  1
  loss:     0.149
  accuracy: 0.991
Epoch:  2
  loss:     0.133
  accuracy: 0.991
Epoch:  3
  loss:     0.113
  accuracy: 0.997
Epoch:  4
  loss:     0.101
  accuracy: 0.997

Nazwy metryczne Keras

W TensorFlow 2,0 modele Keras są bardziej spójne temat obsługi nazw metrycznych.

Teraz kiedy przechodzą ciąg na liście metryk, że dokładny ciąg jest używany jako metryki name . Nazwy te są widoczne w historii obiektu zwróconego przez model.fit , aw dziennikach przekazane keras.callbacks . jest ustawiona na ciąg została przekazana w liście metrycznym.

 model.compile(
    optimizer = tf.keras.optimizers.Adam(0.001),
    loss = tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True),
    metrics = ['acc', 'accuracy', tf.keras.metrics.SparseCategoricalAccuracy(name="my_accuracy")])
history = model.fit(train_data)
 
5/5 [==============================] - 0s 6ms/step - loss: 0.1076 - acc: 0.9969 - accuracy: 0.9969 - my_accuracy: 0.9969

 history.history.keys()
 
dict_keys(['loss', 'acc', 'accuracy', 'my_accuracy'])

Różni się on od poprzednich wersjach, gdzie przechodzące metrics=["accuracy"] powodowałyby dict_keys(['loss', 'acc'])

optymalizujące Keras

W optymalizujące w v1.train jak v1.train.AdamOptimizer i v1.train.GradientDescentOptimizer mają odpowiedniki w tf.keras.optimizers .

Konwersja v1.train do keras.optimizers

Oto rzeczy, o których warto pamiętać podczas konwertowania optymalizujące:

Nowe domyślne dla niektórych tf.keras.optimizers

Brak zmiany dla optimizers.SGD , optimizers.Adam lub optimizers.RMSprop .

Następujące kursy nauki domyślne zostały zmienione:

TensorBoard

TensorFlow 2 zawiera znaczące zmiany w tf.summary API używane do zapisu danych sumarycznych do wizualizacji w TensorBoard. Dla ogólnego wprowadzenia do nowego tf.summary , istnieje kilka tutoriali dostępnych używające TF 2 API. Obejmuje to TensorBoard TF 2 Migration Guide

Zapisywanie i Ładowanie

kompatybilność Checkpoint

TensorFlow 2,0 zastosowania obiektu oparte punktów kontrolnych .

Nazwa punkty kontrolne oparte na starym stylu można jeszcze załadowany, jeśli jesteś ostrożny. Proces konwersji kodu może spowodować zmiany nazw zmiennych, ale istnieją sposoby ich obejścia.

Najprostsze podejście to wyrównać nazwy nowego modelu z nazwami w punkcie kontrolnym:

  • Zmienne nadal wszyscy mają name argumentu można ustawić.
  • Modele Keras wziąć również name argumentu za którą ustawiony jako przedrostek dla swoich zmiennych.
  • v1.name_scope funkcja może być używany do ustawiania zmiennych przedrostki nazw. Jest to bardzo różni się od tf.variable_scope . Wpływa tylko nazwy, a nie śledzić zmienne i ponownego wykorzystania.

Jeśli to nie działa dla przypadków użycia, spróbuj v1.train.init_from_checkpoint funkcję. Zajmuje assignment_map argument, który określa odwzorowanie z nazw starych do nowych nazw.

Repozytorium TensorFlow Estymator zawiera narzędzie do konwersji , aby uaktualnić punkty kontrolne dla estymatorów predefiniowanych z TensorFlow 1.X do 2,0. Może on służyć jako przykład jak zbudować narzędzie podobnym zastosowaniu przypadku.

Zapisane kompatybilność modele

Nie występują znaczne problemy z kompatybilnością dla zapisanych modeli.

  • TensorFlow 1.x saved_models praca w TensorFlow 2.x.
  • TensorFlow 2.x saved_models praca w TensorFlow 1.x-jeśli wszystkie ops są obsługiwane.

Graph.pb lub Graph.pbtxt

Nie ma prosty sposób uaktualnić surowego Graph.pb plik TensorFlow 2.0. Najprościej jest, aby uaktualnić kod wygenerowany plik.

Ale jeśli masz „Frozen graph” (A tf.Graph gdzie zmienne zostały przekształcone stałymi), to jest możliwe, aby przekształcić to do concrete_function wykorzystaniem v1.wrap_function :

 def wrap_frozen_graph(graph_def, inputs, outputs):
  def _imports_graph_def():
    tf.compat.v1.import_graph_def(graph_def, name="")
  wrapped_import = tf.compat.v1.wrap_function(_imports_graph_def, [])
  import_graph = wrapped_import.graph
  return wrapped_import.prune(
      tf.nest.map_structure(import_graph.as_graph_element, inputs),
      tf.nest.map_structure(import_graph.as_graph_element, outputs))
 

Na przykład o to frozed wykres dla Incepcja v1, od 2016 roku:

 path = tf.keras.utils.get_file(
    'inception_v1_2016_08_28_frozen.pb',
    'http://storage.googleapis.com/download.tensorflow.org/models/inception_v1_2016_08_28_frozen.pb.tar.gz',
    untar=True)
 
Downloading data from http://storage.googleapis.com/download.tensorflow.org/models/inception_v1_2016_08_28_frozen.pb.tar.gz
24698880/24695710 [==============================] - 1s 0us/step

Załaduj tf.GraphDef :

 graph_def = tf.compat.v1.GraphDef()
loaded = graph_def.ParseFromString(open(path,'rb').read())
 

Owinąć go w concrete_function :

 inception_func = wrap_frozen_graph(
    graph_def, inputs='input:0',
    outputs='InceptionV1/InceptionV1/Mixed_3b/Branch_1/Conv2d_0a_1x1/Relu:0')
 

Przekazać ją tensora jako wejścia:

 input_img = tf.ones([1,224,224,3], dtype=tf.float32)
inception_func(input_img).shape
 
TensorShape([1, 28, 28, 96])

estymatory

Szkolenie z estymatorów

Estymatory są obsługiwane w TensorFlow 2.0.

Podczas korzystania estymatorów, można użyć input_fn() , tf.estimator.TrainSpec i tf.estimator.EvalSpec z TensorFlow 1.x.

Oto przykład z użyciem input_fn z pociągu i oceny specyfikacje.

Tworzenie input_fn i Pociąg / eval specyfikacje

 # Define the estimator's input_fn
def input_fn():
  datasets, info = tfds.load(name='mnist', with_info=True, as_supervised=True)
  mnist_train, mnist_test = datasets['train'], datasets['test']

  BUFFER_SIZE = 10000
  BATCH_SIZE = 64

  def scale(image, label):
    image = tf.cast(image, tf.float32)
    image /= 255

    return image, label[..., tf.newaxis]

  train_data = mnist_train.map(scale).shuffle(BUFFER_SIZE).batch(BATCH_SIZE)
  return train_data.repeat()

# Define train & eval specs
train_spec = tf.estimator.TrainSpec(input_fn=input_fn,
                                    max_steps=STEPS_PER_EPOCH * NUM_EPOCHS)
eval_spec = tf.estimator.EvalSpec(input_fn=input_fn,
                                  steps=STEPS_PER_EPOCH)

 

Stosując definicję modelu Keras

Istnieją pewne różnice w jak skonstruować swoje estymatory w TensorFlow 2.0.

Zaleca się, aby zdefiniować swój model używając Keras, a następnie użyć tf.keras.estimator.model_to_estimator narzędzia, aby włączyć swój model do estymatora. Poniższy kod pokazuje, jak używać tego narzędzia podczas tworzenia i szkolenia estymator.

 def make_model():
  return tf.keras.Sequential([
    tf.keras.layers.Conv2D(32, 3, activation='relu',
                           kernel_regularizer=tf.keras.regularizers.l2(0.02),
                           input_shape=(28, 28, 1)),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dropout(0.1),
    tf.keras.layers.Dense(64, activation='relu'),
    tf.keras.layers.BatchNormalization(),
    tf.keras.layers.Dense(10)
  ])
 
 model = make_model()

model.compile(optimizer='adam',
              loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True),
              metrics=['accuracy'])

estimator = tf.keras.estimator.model_to_estimator(
  keras_model = model
)

tf.estimator.train_and_evaluate(estimator, train_spec, eval_spec)
 
INFO:tensorflow:Using default config.

INFO:tensorflow:Using default config.

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmpb3_a632k

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmpb3_a632k

INFO:tensorflow:Using the Keras model provided.

INFO:tensorflow:Using the Keras model provided.

Warning:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.6/site-packages/tensorflow/python/ops/resource_variable_ops.py:1666: calling BaseResourceVariable.__init__ (from tensorflow.python.ops.resource_variable_ops) with constraint is deprecated and will be removed in a future version.
Instructions for updating:
If using Keras pass *_constraint arguments to layers.

Warning:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.6/site-packages/tensorflow/python/ops/resource_variable_ops.py:1666: calling BaseResourceVariable.__init__ (from tensorflow.python.ops.resource_variable_ops) with constraint is deprecated and will be removed in a future version.
Instructions for updating:
If using Keras pass *_constraint arguments to layers.

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmpb3_a632k', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmpb3_a632k', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

Warning:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.6/site-packages/tensorflow/python/training/training_util.py:236: Variable.initialized_value (from tensorflow.python.ops.variables) is deprecated and will be removed in a future version.
Instructions for updating:
Use Variable.read_value. Variables in 2.X are initialized automatically both in eager and graph (inside tf.defun) contexts.

Warning:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.6/site-packages/tensorflow/python/training/training_util.py:236: Variable.initialized_value (from tensorflow.python.ops.variables) is deprecated and will be removed in a future version.
Instructions for updating:
Use Variable.read_value. Variables in 2.X are initialized automatically both in eager and graph (inside tf.defun) contexts.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Warm-starting with WarmStartSettings: WarmStartSettings(ckpt_to_initialize_from='/tmp/tmpb3_a632k/keras/keras_model.ckpt', vars_to_warm_start='.*', var_name_to_vocab_info={}, var_name_to_prev_var_name={})

INFO:tensorflow:Warm-starting with WarmStartSettings: WarmStartSettings(ckpt_to_initialize_from='/tmp/tmpb3_a632k/keras/keras_model.ckpt', vars_to_warm_start='.*', var_name_to_vocab_info={}, var_name_to_prev_var_name={})

INFO:tensorflow:Warm-starting from: /tmp/tmpb3_a632k/keras/keras_model.ckpt

INFO:tensorflow:Warm-starting from: /tmp/tmpb3_a632k/keras/keras_model.ckpt

INFO:tensorflow:Warm-starting variables only in TRAINABLE_VARIABLES.

INFO:tensorflow:Warm-starting variables only in TRAINABLE_VARIABLES.

INFO:tensorflow:Warm-started 8 variables.

INFO:tensorflow:Warm-started 8 variables.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmpb3_a632k/model.ckpt.

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmpb3_a632k/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:loss = 2.270717, step = 0

INFO:tensorflow:loss = 2.270717, step = 0

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmpb3_a632k/model.ckpt.

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmpb3_a632k/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:32Z

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:32Z

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Restoring parameters from /tmp/tmpb3_a632k/model.ckpt-25

INFO:tensorflow:Restoring parameters from /tmp/tmpb3_a632k/model.ckpt-25

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Inference Time : 1.01619s

INFO:tensorflow:Inference Time : 1.01619s

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:33

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:33

INFO:tensorflow:Saving dict for global step 25: accuracy = 0.671875, global_step = 25, loss = 1.5162958

INFO:tensorflow:Saving dict for global step 25: accuracy = 0.671875, global_step = 25, loss = 1.5162958

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmpb3_a632k/model.ckpt-25

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmpb3_a632k/model.ckpt-25

INFO:tensorflow:Loss for final step: 0.39261085.

INFO:tensorflow:Loss for final step: 0.39261085.

({'accuracy': 0.671875, 'loss': 1.5162958, 'global_step': 25}, [])

Korzystanie z niestandardowego model_fn

Jeśli masz już zwyczaj estymatora model_fn że trzeba utrzymać, można konwertować model_fn do korzystania z modelu Keras.

Jednakże, ze względu na kompatybilność, zwyczaj model_fn będzie nadal działać w trybie wykresu 1.x stylu. Oznacza to, że nie jest chętny wykonanie i brak zależności automatyczne sterowanie.

model_fn zwyczaj z minimalnymi zmianami

Aby dokonać niestandardowego model_fn pracę w TF 2.0, jeśli wolisz minimalnych zmian w istniejącym kodzie tf.compat.v1 symbole takie jak optimizers i metrics mogą być użyte.

Stosując modele Keras w niestandardowym model_fn jest podobna do używania go w pętli zwyczaj szkoleniowej:

  • Ustaw training fazę odpowiednio, w oparciu o mode argument.
  • Wyraźnie zdać modelki trainable_variables do optymalizatora.

Ale istnieją istotne różnice, w stosunku do niestandardowych pętli :

  • Zamiast używać Model.losses , wyodrębnić straty stosując Model.get_losses_for .
  • Wyciąg aktualizacje modelki stosując Model.get_updates_for .

Poniższy kod tworzy prognozy z niestandardowym model_fn , ilustrującym wszystkie te obawy.

 def my_model_fn(features, labels, mode):
  model = make_model()

  optimizer = tf.compat.v1.train.AdamOptimizer()
  loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True)

  training = (mode == tf.estimator.ModeKeys.TRAIN)
  predictions = model(features, training=training)

  if mode == tf.estimator.ModeKeys.PREDICT:
    return tf.estimator.EstimatorSpec(mode=mode, predictions=predictions)

  reg_losses = model.get_losses_for(None) + model.get_losses_for(features)
  total_loss=loss_fn(labels, predictions) + tf.math.add_n(reg_losses)

  accuracy = tf.compat.v1.metrics.accuracy(labels=labels,
                                           predictions=tf.math.argmax(predictions, axis=1),
                                           name='acc_op')

  update_ops = model.get_updates_for(None) + model.get_updates_for(features)
  minimize_op = optimizer.minimize(
      total_loss,
      var_list=model.trainable_variables,
      global_step=tf.compat.v1.train.get_or_create_global_step())
  train_op = tf.group(minimize_op, update_ops)

  return tf.estimator.EstimatorSpec(
    mode=mode,
    predictions=predictions,
    loss=total_loss,
    train_op=train_op, eval_metric_ops={'accuracy': accuracy})

# Create the Estimator & Train
estimator = tf.estimator.Estimator(model_fn=my_model_fn)
tf.estimator.train_and_evaluate(estimator, train_spec, eval_spec)
 
INFO:tensorflow:Using default config.

INFO:tensorflow:Using default config.

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmpjb2yik9a

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmpjb2yik9a

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmpjb2yik9a', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmpjb2yik9a', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmpjb2yik9a/model.ckpt.

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmpjb2yik9a/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:loss = 2.6231384, step = 0

INFO:tensorflow:loss = 2.6231384, step = 0

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmpjb2yik9a/model.ckpt.

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmpjb2yik9a/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:36Z

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:36Z

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Restoring parameters from /tmp/tmpjb2yik9a/model.ckpt-25

INFO:tensorflow:Restoring parameters from /tmp/tmpjb2yik9a/model.ckpt-25

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Inference Time : 1.09900s

INFO:tensorflow:Inference Time : 1.09900s

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:37

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:37

INFO:tensorflow:Saving dict for global step 25: accuracy = 0.621875, global_step = 25, loss = 1.6634324

INFO:tensorflow:Saving dict for global step 25: accuracy = 0.621875, global_step = 25, loss = 1.6634324

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmpjb2yik9a/model.ckpt-25

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmpjb2yik9a/model.ckpt-25

INFO:tensorflow:Loss for final step: 0.56862533.

INFO:tensorflow:Loss for final step: 0.56862533.

({'accuracy': 0.621875, 'loss': 1.6634324, 'global_step': 25}, [])

Custom model_fn z TF 2,0 symboli

Jeśli chcesz pozbyć się wszystkich symboli 1.x TF i uaktualnić swój własny model_fn do rodzimej TF 2.0, trzeba zaktualizować Optimizer i metryk do tf.keras.optimizers i tf.keras.metrics .

W niestandardowym model_fn , oprócz powyższych zmian , więcej uaktualnień należy dokonać:

W powyższym przykładzie my_model_fn kod po migracji 2,0 symboli przedstawione jako:

 def my_model_fn(features, labels, mode):
  model = make_model()

  training = (mode == tf.estimator.ModeKeys.TRAIN)
  loss_obj = tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True)
  predictions = model(features, training=training)

  # Get both the unconditional losses (the None part)
  # and the input-conditional losses (the features part).
  reg_losses = model.get_losses_for(None) + model.get_losses_for(features)
  total_loss=loss_obj(labels, predictions) + tf.math.add_n(reg_losses)

  # Upgrade to tf.keras.metrics.
  accuracy_obj = tf.keras.metrics.Accuracy(name='acc_obj')
  accuracy = accuracy_obj.update_state(
      y_true=labels, y_pred=tf.math.argmax(predictions, axis=1))

  train_op = None
  if training:
    # Upgrade to tf.keras.optimizers.
    optimizer = tf.keras.optimizers.Adam()
    # Manually assign tf.compat.v1.global_step variable to optimizer.iterations
    # to make tf.compat.v1.train.global_step increased correctly.
    # This assignment is a must for any `tf.train.SessionRunHook` specified in
    # estimator, as SessionRunHooks rely on global step.
    optimizer.iterations = tf.compat.v1.train.get_or_create_global_step()
    # Get both the unconditional updates (the None part)
    # and the input-conditional updates (the features part).
    update_ops = model.get_updates_for(None) + model.get_updates_for(features)
    # Compute the minimize_op.
    minimize_op = optimizer.get_updates(
        total_loss,
        model.trainable_variables)[0]
    train_op = tf.group(minimize_op, *update_ops)

  return tf.estimator.EstimatorSpec(
    mode=mode,
    predictions=predictions,
    loss=total_loss,
    train_op=train_op,
    eval_metric_ops={'Accuracy': accuracy_obj})

# Create the Estimator & Train.
estimator = tf.estimator.Estimator(model_fn=my_model_fn)
tf.estimator.train_and_evaluate(estimator, train_spec, eval_spec)
 
INFO:tensorflow:Using default config.

INFO:tensorflow:Using default config.

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmppkb1q1hq

Warning:tensorflow:Using temporary folder as model directory: /tmp/tmppkb1q1hq

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmppkb1q1hq', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Using config: {'_model_dir': '/tmp/tmppkb1q1hq', '_tf_random_seed': None, '_save_summary_steps': 100, '_save_checkpoints_steps': None, '_save_checkpoints_secs': 600, '_session_config': allow_soft_placement: true
graph_options {
  rewrite_options {
    meta_optimizer_iterations: ONE
  }
}
, '_keep_checkpoint_max': 5, '_keep_checkpoint_every_n_hours': 10000, '_log_step_count_steps': 100, '_train_distribute': None, '_device_fn': None, '_protocol': None, '_eval_distribute': None, '_experimental_distribute': None, '_experimental_max_worker_delay_secs': None, '_session_creation_timeout_secs': 7200, '_service': None, '_cluster_spec': ClusterSpec({}), '_task_type': 'worker', '_task_id': 0, '_global_id_in_cluster': 0, '_master': '', '_evaluation_master': '', '_is_chief': True, '_num_ps_replicas': 0, '_num_worker_replicas': 1}

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Not using Distribute Coordinator.

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Running training and evaluation locally (non-distributed).

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after every checkpoint. Checkpoint frequency is determined based on RunConfig arguments: save_checkpoints_steps None or save_checkpoints_secs 600.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Create CheckpointSaverHook.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 0...

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmppkb1q1hq/model.ckpt.

INFO:tensorflow:Saving checkpoints for 0 into /tmp/tmppkb1q1hq/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 0...

INFO:tensorflow:loss = 2.6947184, step = 0

INFO:tensorflow:loss = 2.6947184, step = 0

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners before saving checkpoint 25...

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmppkb1q1hq/model.ckpt.

INFO:tensorflow:Saving checkpoints for 25 into /tmp/tmppkb1q1hq/model.ckpt.

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling checkpoint listeners after saving checkpoint 25...

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Done calling model_fn.

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:40Z

INFO:tensorflow:Starting evaluation at 2020-07-23T01:32:40Z

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Graph was finalized.

INFO:tensorflow:Restoring parameters from /tmp/tmppkb1q1hq/model.ckpt-25

INFO:tensorflow:Restoring parameters from /tmp/tmppkb1q1hq/model.ckpt-25

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Done running local_init_op.

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [1/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [2/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [3/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [4/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Evaluation [5/5]

INFO:tensorflow:Inference Time : 1.05743s

INFO:tensorflow:Inference Time : 1.05743s

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:41

INFO:tensorflow:Finished evaluation at 2020-07-23-01:32:41

INFO:tensorflow:Saving dict for global step 25: Accuracy = 0.784375, global_step = 25, loss = 1.4717665

INFO:tensorflow:Saving dict for global step 25: Accuracy = 0.784375, global_step = 25, loss = 1.4717665

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmppkb1q1hq/model.ckpt-25

INFO:tensorflow:Saving 'checkpoint_path' summary for global step 25: /tmp/tmppkb1q1hq/model.ckpt-25

INFO:tensorflow:Loss for final step: 0.5751184.

INFO:tensorflow:Loss for final step: 0.5751184.

({'Accuracy': 0.784375, 'loss': 1.4717665, 'global_step': 25}, [])

premade Estymatory

Premade Estymatory w rodzinie tf.estimator.DNN* , tf.estimator.Linear* i tf.estimator.DNNLinearCombined* nadal są obsługiwane w API TensorFlow 2.0, jednak pewne argumenty zostały zmienione:

  1. input_layer_partitioner : Usunięty w 2,0.
  2. loss_reduction : Aktualizacja do tf.keras.losses.Reduction zamiast tf.compat.v1.losses.Reduction . Jego wartość domyślna jest również zmieniona na tf.keras.losses.Reduction.SUM_OVER_BATCH_SIZE z tf.compat.v1.losses.Reduction.SUM .
  3. optimizer , dnn_optimizer i linear_optimizer : arg ten został zaktualizowany do tf.keras.optimizers zamiast tf.compat.v1.train.Optimizer .

Migrować powyższych zmian:

  1. Nie potrzebna jest migracja do input_layer_partitioner od Distribution Strategy będzie go obsługiwać automatycznie w TF 2.0.
  2. Dla loss_reduction sprawdzić tf.keras.losses.Reduction dla obsługiwanych opcji.
  3. Dla optimizer args, jeśli nie przechodzą w optimizer , dnn_optimizer lub linear_optimizer Arg, lub jeśli podasz optimizer argumentu jako string w kodzie, nie trzeba niczego zmieniać. tf.keras.optimizers jest używany domyślnie. W przeciwnym razie trzeba zaktualizować go z tf.compat.v1.train.Optimizer odpowiednio jego tf.keras.optimizers

Checkpoint Converter

Migracja do keras.optimizers złamie punktów kontrolnych zapisanych za pomocą TF 1.x, jak tf.keras.optimizers generuje inny zestaw zmiennych, które mają być zapisane w punktach kontrolnych. Aby stary checkpoint wielokrotnego użytku po migracji do TF 2.0, spróbuj konwerter checkpoint .

 curl -O https://raw.githubusercontent.com/tensorflow/estimator/master/tensorflow_estimator/python/estimator/tools/checkpoint_converter.py
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100 15157  100 15157    0     0  63684      0 --:--:-- --:--:-- --:--:-- 63684

Narzędzie posiada wbudowane pomoc:

 python checkpoint_converter.py -h
usage: checkpoint_converter.py [-h]
                               {dnn,linear,combined} source_checkpoint
                               source_graph target_checkpoint

positional arguments:
  {dnn,linear,combined}
                        The type of estimator to be converted. So far, the
                        checkpoint converter only supports Canned Estimator.
                        So the allowed types include linear, dnn and combined.
  source_checkpoint     Path to source checkpoint file to be read in.
  source_graph          Path to source graph file to be read in.
  target_checkpoint     Path to checkpoint file to be written out.

optional arguments:
  -h, --help            show this help message and exit

TensorShape

Klasa ta została uproszczona do hold int s, zamiast tf.compat.v1.Dimension obiektów. Więc nie ma potrzeby, aby zadzwonić .value() , aby uzyskać int .

Indywidualne tf.compat.v1.Dimension obiekty są nadal dostępne z tf.TensorShape.dims .

Dodaje się wykazać różnice między TensorFlow 1.x oraz TensorFlow 2.0.

 # Create a shape and choose an index
i = 0
shape = tf.TensorShape([16, None, 256])
shape
 
TensorShape([16, None, 256])

Jeśli miał to w TF 1.x:

 value = shape[i].value
 

Wtedy to zrobić w TF 2.0:

 value = shape[i]
value
 
16

Jeśli miał to w TF 1.x:

 for dim in shape:
    value = dim.value
    print(value)
 

Wtedy to zrobić w TF 2.0:

 for value in shape:
  print(value)
 
16
None
256

Jeśli miał to w TF 1.x (lub stosowane inne metody wymiarowania):

 dim = shape[i]
dim.assert_is_compatible_with(other_dim)
 

Wtedy to zrobić w TF 2.0:

 other_dim = 16
Dimension = tf.compat.v1.Dimension

if shape.rank is None:
  dim = Dimension(None)
else:
  dim = shape.dims[i]
dim.is_compatible_with(other_dim) # or any other dimension method
 
True
 shape = tf.TensorShape(None)

if shape:
  dim = shape.dims[i]
  dim.is_compatible_with(other_dim) # or any other dimension method
 

Wartość logiczna wartość tf.TensorShape jest True jeśli ranga jest znana, False w przeciwnym razie.

 print(bool(tf.TensorShape([])))      # Scalar
print(bool(tf.TensorShape([0])))     # 0-length vector
print(bool(tf.TensorShape([1])))     # 1-length vector
print(bool(tf.TensorShape([None])))  # Unknown-length vector
print(bool(tf.TensorShape([1, 10, 100])))       # 3D tensor
print(bool(tf.TensorShape([None, None, None]))) # 3D tensor with no known dimensions
print()
print(bool(tf.TensorShape(None)))  # A tensor with unknown rank.
 
True
True
True
True
True
True

False

Inne zmiany

  • Usuń tf.colocate_with : algorytmy pośrednictwa urządzenie TensorFlow za znacznie się poprawiła. To nie powinno być konieczne. Jeśli usunięcie go powoduje degradacją wydajności należy zgłosić błąd .

  • Wymienić v1.ConfigProto wykorzystania z odpowiednimi funkcjami z tf.config .

wnioski

Cały proces jest:

  1. Uruchomić skrypt aktualizacyjny.
  2. Usunąć symbole contrib.
  3. Przełączyć swoje modele do stylu zorientowanego obiektowo (Keras).
  4. Stosować tf.keras lub tf.estimator szkolenia i pętle oceny gdzie można.
  5. W przeciwnym razie, pętle użycie niestandardowych, ale należy unikać sesje i zbiory.

To zajmuje trochę pracy do kodu konwertować do idiomatycznym TensorFlow 2.0, ale co zmiana powoduje:

  • Mniejsza liczba linii kodu.
  • Zwiększona przejrzystość i prostotę.
  • Łatwiejsze debugowanie.