NotImplementedError при использовании model.save () в Keras - PullRequest
0 голосов
/ 26 марта 2019

NotImplementedError при использовании model.save () в Keras

Я пытаюсь использовать Keras для реализации простой модели кодер-декодер.Я не использовал Sequential ().Я попробовал Подкласс Модели.Я успешно обучил модель, но не смог ее сохранить.Сначала я не добавил input_shape для первого слоя моделей.Но когда я добавляю его в модель, происходит такая же ошибка.И я не знаю, как его сохранить.

import tensorflow as tf

import numpy as np
import time
import matplotlib.pyplot as plt

import caption_preprocessing
import train_dataset_preparation

tf.enable_eager_execution()

# some parameters
voc_size = len(caption_preprocessing.tokenizer.word_index)  # voc_size = 10001
embedding_output_dim = 256
lstm_output_dim = 512
encoder_output_dim = embedding_output_dim

EPOCHS = 1


# model definition
class EncoderPart(tf.keras.Model):
    def __init__(self):
        super(EncoderPart, self).__init__()
        self.fc = tf.keras.layers.Dense(input_shape=(64, 2048), units=encoder_output_dim)

    def call(self, inputs, training=None, mask=None):
        y = self.fc(inputs)
        output = tf.nn.relu(y)
        return output


class EmbeddingPart(tf.keras.Model):
    def __init__(self):
        super(EmbeddingPart, self).__init__()
        self.embedding = tf.keras.layers.Embedding(input_shape=(1,),
                                                   input_dim=voc_size,
                                                   output_dim=embedding_output_dim)

    def call(self, inputs, training=None, mask=None):
        output = self.embedding(inputs)
        return output


class DecoderPart(tf.keras.Model):
    def __init__(self):
        super(DecoderPart, self).__init__()
        self.lstm = tf.keras.layers.CuDNNLSTM(input_shape=(64, embedding_output_dim),
                                              units=lstm_output_dim,
                                              return_sequences=True,
                                              return_state=True,
                                              recurrent_initializer='glorot_uniform')
        self.fc = tf.keras.layers.Dense(units=voc_size)

    def call(self, inputs, training=None, mask=None):
        y, state_h, state_c = self.lstm(inputs)
        output = self.fc(y)
        return output, state_c

    def reset_states(self, batch_size):
        return tf.zeros((batch_size, lstm_output_dim))


def _loss_function(real, pred):
    mask = 1 - np.equal(real, 0)    # ignore the loss of padding words
    loss = tf.nn.sparse_softmax_cross_entropy_with_logits(labels=real, logits=pred) * mask
    return tf.reduce_mean(loss)


if __name__ == '__main__':
    # training model
    encoder = EncoderPart()
    embedding = EmbeddingPart()
    decoder = DecoderPart()

    optimizer = tf.train.AdamOptimizer()

    loss_plot = []

    time_per_epoch = time.time()
    for epoch in range(EPOCHS):
        start_time = time.time()
        total_loss = 0

        for (batch, (image_feature_vec, caption)) in enumerate(train_dataset_preparation.dataset):
            # print(batch+1, caption.shape)
            batch_loss = 0
            decoder.reset_states(caption.shape[0])  # reset the states of the lstm layer
            start_vec = [caption_preprocessing.tokenizer.word_index['<start>']] * caption.shape[0]
            dec_input = tf.expand_dims(start_vec, 1)    # shape=(BATCH_SIZE, 1)

            with tf.GradientTape() as tape:
                image_feature = encoder(image_feature_vec)
                _, state = decoder(image_feature)   # _.shape=(BATCH_SIZE, 64, 10001), state.shape=(BATCH_SIZE, 512)

                for i in range(1, caption.shape[1]):
                    word_embedding = embedding(dec_input)   # shape=(BATCH_SIZE, 1, embedding_output_dim)
                    predictions, _ = decoder(word_embedding)    # shape=(BATCH_SIZE, 1, voc_size)
                    predictions = tf.reshape(predictions, (caption.shape[0], -1))   # shape=(BATCH_SIZE, embedding_output_dim)
                    batch_loss += _loss_function(caption[:, i], predictions)

                    dec_input = tf.expand_dims(caption[:, i], 1)

            total_loss += (batch_loss / int(caption.shape[1]))

            variables = encoder.variables + embedding.variables + decoder.variables
            gradients = tape.gradient(batch_loss, variables)
            optimizer.apply_gradients(zip(gradients, variables), tf.train.get_or_create_global_step())

            if (batch + 1) % 100 == 0:
                print('Epoch {} Batch {} Loss {:.4f}'.format(epoch + 1,
                                                         batch + 1,
                                                         batch_loss.numpy() / int(caption.shape[1])))

    loss_plot.append(total_loss / len(caption_preprocessing.train_cap_vec))
    print('Epoch {} Loss {:.6f}'.format(epoch + 1,
                                        total_loss / len(caption_preprocessing.train_cap_vec)))
    print('Time taken for 1 epoch {} sec\n'.format(time.time() - start_time))

time_per_epoch = (time.time() - time_per_epoch) / EPOCHS

# loss plot
plt.plot(loss_plot)
plt.xlabel('epochs')
plt.ylabel('loss')
plt.title('loss plot')
plt.show()

# save model
save_path = r'\20190326'

encoder _save_file = r'C:\Users\LZ_Jaja\PycharmProjects\Show_and_Tell_190314\model_and_eval' + save_path + r'\encoder.h5'

tf.keras.models.save_model(encoder, embedding_w_save_file)

Я пробовал model.save() и tf.keras.models.save_model().Оба они вызывают одну и ту же ошибку.Ниже приведена ошибка:

Traceback (последний вызов был последним): файл "C: /Users/LZ_Jaja/PycharmProjects/Show_and_Tell_190314/model_train_and_save.py", строка 138, в файле tf.keras.models.save_model (кодировщик, embedding_w_save_file) Файл "C: \ Users \ LZ_Jaja \ Anaconda3 \ envs \ensorflow_gpu \ lib \ site-packages \ tenorflow \ python \ keras \ engine \ save.py", строка 101, в save_model 'config': модель.get_config () Файл "C: \ Users \ LZ_Jaja \ Anaconda3 \ envs \ensorflow_gpu \ lib \ site-packages \ensorflow \ python \ keras \ engine \ network.py", строка 1111, в get_config поднять NotImplementedError NotImplementedError

Я также пытался сохранить архитектуру и веса соответственно, но при использовании model.to_yaml() также возникает ошибка.

model.save_weights() действует.Но при загрузке весов с помощью model.load_weights() возникает ошибка, в которой говорится, что я пытаюсь заполнить 0 слой весами с 1 слоем (я точно забываю информацию об ошибке).

Так что мне нужна помощь.Как сохранить модель и правильно загрузить ее?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...