Keras自定义损失函数,利用另一个模型显示不兼容的形状误差

时间:2019-07-16 16:35:33

标签: python tensorflow keras loss-function

我有一个figure所示的卷积模型(main_model)。 该模型拍摄(896,896,3)个图像并生成(448,448,100)个特征。由于此模型的输出很大,因此无法生成目标数据。相反,我想使用另一个模型(const_model)生成目标并将目标插入损失函数中。

以下是我的琐碎实现。

import keras
from keras.models import Model
from keras.layers import Conv2D, MaxPooling2D, Input
import numpy as np


# main_model
input_layer=Input(shape=(896,896,3))
new_layer = Conv2D(filters=32, kernel_size=(3,3), padding="same")(input_layer)
new_layer = MaxPooling2D(pool_size=(2, 2), strides=(2,2), padding='same')(new_layer)
new_layer = Conv2D(filters=100, kernel_size=(3,3), dilation_rate=4, padding="same", name="dilation_1")(new_layer)
main_model = Model(input_layer, new_layer)

# const_model
y=input_layer #same input tensor from the main_model
y = Conv2D(filters=100, kernel_size=(3,3), padding="same", trainable=False, kernel_initializer='he_normal', name="non_trainable_layer")(y)
y=MaxPooling2D(pool_size=(2, 2), strides=(2,2), padding='same')(y)
constant_model=Model(input_layer, y)

constant_model.trainable=False
for l in constant_model.layers:
    l.trainable=False

def custom_loss_wrapper(constant_model):
    def custom_loss(y_true, y_pred):
        eval_true=constant_model(y_true)
        loss= keras.losses.mean_absolute_error(eval_true, y_pred)
        return loss
    return custom_loss

main_model.compile(optimizer='adam',
          loss=custom_loss_wrapper(constant_model),
          metrics=['accuracy'])

X_train = np.random.random(size=(10, 896, 896, 3))

history = main_model.fit(x=X_train, y=X_train, batch_size=2, epochs=10, verbose=True)

这会产生以下错误:

  File "fully_conv_bsnet/RGB_2.py", line 256, in do_RGB_seed
    batch_size=2
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/keras/engine/training.py", line 1039, in fit
    validation_steps=validation_steps)
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/keras/engine/training_arrays.py", line 199, in fit_loop
    outs = f(ins_batch)
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/keras/backend/tensorflow_backend.py", line 2715, in __call__
    return self._call(inputs)
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/keras/backend/tensorflow_backend.py", line 2675, in _call
    fetched = self._callable_fn(*array_vals)
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/tensorflow/python/client/session.py", line 1454, in __call__
    self._session._session, self._handle, args, status, None)
  File "/home/shaon/myenv/p1/lib/python3.6/site-packages/tensorflow/python/framework/errors_impl.py", line 519, in __exit__
    c_api.TF_GetCode(self.status.status))
tensorflow.python.framework.errors_impl.InvalidArgumentError: Incompatible shapes: [2,896,896] vs. [2,448,448]
     [[Node: metrics_1/acc/Equal = Equal[T=DT_INT64, _device="/job:localhost/replica:0/task:0/device:GPU:0"](metrics_1/acc/ArgMax, metrics_1/acc/ArgMax_1)]]
     [[Node: loss_1/mul/_99 = _Recv[client_terminated=false, recv_device="/job:localhost/replica:0/task:0/device:CPU:0", send_device="/job:localhost/replica:0/task:0/device:GPU:0", send_device_incarnation=1, tensor_name="edge_440_loss_1/mul", tensor_type=DT_FLOAT, _device="/job:localhost/replica:0/task:0/device:CPU:0"]()]]

我认为问题是由于y_truey_pred之间的形状不兼容,因为当输入层和输出层具有相同的形状时(如果我不使用双斜线{ {1}}层,那么培训就没有问题。

有人可以帮忙吗?

0 个答案:

没有答案