Пользовательский слой Keras Tensorflow вызывается только один раз

#python #tensorflow #keras #tensorflow2.0 #keras-layer

Вопрос:

После двух дней интенсивных поисков я не нашел ответов в документах keras/стопке.

Я пытаюсь создать пользовательский слой для выполнения увеличения каждой партии с некоторой вероятностью (теперь 1 для демонстрации). данные представляют собой изображение с одним каналом.

Мне нужен способ узнать, действительно ли увеличение происходит во время тренировки, потому что отпечатки внутри функций увеличения происходят только один раз, когда определена сеть, и еще один, когда fit функция активирована.

любая помощь будет очень признательна, спасибо!

Базовый рабочий пример для выполнения, обратите внимание на количество отпечатков с call() :

 from tensorflow.keras.layers import Input, Dense, Conv2D, Flatten
from tensorflow.keras.models import Sequential
import random
import numpy as np
import tensorflow as tf
from tensorflow.keras import optimizers


# Custom Augmentation layer
class AugmentationLayer(tf.keras.layers.Layer):
    def __init__(self, p):
        super(AugmentationLayer, self).__init__()
        self.p = p

    def call(self, inputs, training=None):
        if not training:
            return inputs
        print('Enter Custom layer call, training = ', training)
        
        if random.random() < self.p:  
            inputs *= 2
        return inputs

# Training Script

# parameters
height = 38
width = 22
numClasses = 2
ydata = np.array([[1, 0], [1, 0]])   # hot-encoded labels

# create 2 images for network training data
Xdata = []
for i in range(2):
    xx = np.random.uniform(-1, 1, (height, width))
    Xdata.append(xx)

# create array from list
Xdata = np.array(Xdata)

# make dims n_samples X height X width X channels = (2, 38, 22, 1)
Xdata = np.reshape(Xdata, (Xdata.shape[0], Xdata.shape[1], Xdata.shape[2], 1))

model = Sequential()
model.add(Input(shape=(height, width, 1)))
model.add(AugmentationLayer(1))                   # Added custom layer
model.add(Conv2D(32, (2, 2), activation='relu'))
model.add(Flatten())
model.add(Dense(numClasses, activation='softmax'))

model.compile(
    loss='categorical_crossentropy',
    metrics=['accuracy'],
    optimizer=optimizers.Adam(learning_rate=0.001))

model.summary()

model.fit(
    Xdata,
    ydata,
    epochs=10,
    batch_size=2,
    verbose=1)
 

Комментарии:

1. Слои вызываются один раз для построения графика вычислений, созданного TensorFlow.

Ответ №1:

Если вы используете tf.print() его, он также будет печататься при выполнении графика. Вы можете прочитать больше об этом здесь: https://www.tensorflow.org/api_docs/python/tf/print.

Комментарии:

1. именно то, что я искал! когда я использовал tf.print (), сообщение выводилось на стандартный вывод, когда я ожидал, что оно будет — в каждой партии. Спасибо.

Ответ №2:

для кого-то в будущем я добавлю, что при компиляции модели существует значение по умолчанию, которое не позволяет запускать определенные функции внутри пользовательских слоев (вот почему обычная печать() не работала) в целях повышения производительности. среди них: print(), np.save() и, возможно, больше.

 model.compile(..., run_eagerly=False)   # default
 

если вы хотите включить все функции, упомянутые выше, скомпилируйте свою модель с помощью:

 model.compile(..., run_eagerly=True)