如何使用取决于类变量的自定义损失函数保存和加载keras模型?

时间:2020-08-14 13:47:43

标签: python tensorflow keras

我正在创建一个基于LSTM的变体自动编码器。我创建了自己的自定义损失函数,在其中使用了两个不同的类变量pos_weightkl_cofkl_cof在每个时代都在改变它的价值。

 class LSTM_VAE(object):
     
     def __init__(..,pos_weight=None)
     
         ..
         self.kl_cof = K.variable(0.5)
         self.pos_weight = pos_weight
         self.autoencoder = None
         ....

         def vae_loss(x, x_decoded_mean):
            xent_loss = K.mean(x*-K.log(x_decoded_mean)*self.pos_weight+(1-x)*-K.log(1-x_decoded_mean))
            kl_loss = ....
            return xent_loss + K.get_value(self.kl_cof)*kl_loss
            ....
          self.autoencoder.compile(optimizer='Adam',
                     loss=vae_loss,
                     metrics=['accuracy'])

    def train_model(self,X_train,X_val,batch_size,epochs):
          cbk = LambdaCallback(....)
          print_weights = LambdaCallback(....)
          self.autoencoder.fit(x=X_train, y=X_train,batch_size=batch_size,epochs=epochs,callbacks=[self.checkpointer,cbk,print_weights],validation_data=(X_val,X_val))
    ....

self.autoencoder完成训练后,模型将另存为“ lstm_vae.h5”文件。但是当我尝试跑步

  lstm_vae=keras.models.load_model('lstm_vae.h5')

它抛出一个ValueError: Unknown loss function:vae_loss

在其他线程中进行了一些研究之后,它说我应该像这样在custom_object内部传递损失函数

 lstm_vae=keras.models.load_model('lstm_vae.h5',custom_object={'loss':vae_loss})

但是由于我在LSTM_VAE类中定义了损失函数,因此它再次抛出ValueError: Unknown loss function:vae_loss,这是因为损失函数正在使用LSTM_VAE类变量。

那么当我使用此自定义损失函数时如何正确加载模型?

1 个答案:

答案 0 :(得分:0)

尝试一下:

model = load_model("path/to/model.h5", compile=False)
optimizer = Adam(learning_rate=.01)

def vae_loss(x, x_decoded_mean):
    xent_loss = K.mean(x*-K.log(x_decoded_mean)*self.pos_weight+(1-x)*-   K.log(1-x_decoded_mean))
    kl_loss = ....
    return xent_loss + K.get_value(self.kl_cof)*kl_loss

model.compile(optimizer=optimizer, loss=vae_loss, metrics=['accuracy'])

我遇到了同样的问题,未编译就加载了模型,然后在重新编译之前定义损失是对我有用的解决方案