简体   繁体   English

在Keras中编写自定义MSE损失函数

[英]Write a custom MSE loss function in Keras

I'm trying to create an image denoising ConvNet in Keras and I want to create my own loss function. 我正在尝试在Keras中创建一个对ConvNet去噪的图像,并且我想创建自己的损失函数。 I want it to take a noisy image as an input and to get the noise as an output. 我希望它以嘈杂的图像作为输入,并获得噪音作为输出。 This loss function is pretty much like a MSE loss but which will make my network learn to remove the clean image and not the noise from the input noisy image. 此损失功能几乎类似于MSE损失,但它将使我的网络学会删除干净的图像,而不是输入噪声图像中的噪声。

The loss function I want to implement with y the noisy image, x the clean image and R(y) the predicted image: 我想用y噪声图像,x干净图像和R(y)预测图像实现损失函数:

我要实现的损失函数

I've tried to make it by myself but I don't know how to make the loss access to my noisy images since it changes all the time. 我尝试自己制作,但是我不知道如何让嘈杂的图像丢失,因为它一直在变化。

def residual_loss(noisy_img):
  def loss(y_true, y_pred):
    return np.mean(np.square(y_pred - (noisy_img - y_true), axis=-1)
return loss

Basically, what I need to do is something like this : 基本上,我需要做的是这样的:

input_img = Input(shape=(None,None,3))

c1 = Convolution2D(64, (3, 3))(input_img)
a1 = Activation('relu')(c1)

c2 = Convolution2D(64, (3, 3))(a1)
a2 = Activation('relu')(c2)

c3 = Convolution2D(64, (3, 3))(a2)
a3 = Activation('relu')(c3)

c4 = Convolution2D(64, (3, 3))(a3)
a4 = Activation('relu')(c4)

c5 = Convolution2D(3, (3, 3))(a4)
out = Activation('relu')(c5)

model = Model(input_img, out)
model.compile(optimizer='adam', loss=residual_loss(input_img))

But if I try this, I get : 但是,如果我尝试这样做,我会得到:

 IndexError: tuple index out of range

What can I do ? 我能做什么 ?

Since it's quite unusual to use the "input" in the loss function (it's not meant for that), I think it's worth saying: 由于在损失函数中使用“输入”是很不寻常的(这并不意味着要这样做),我认为值得一提:

It's not the role of the loss function to separate the noise. 分离噪声不是损失函数的作用。 The loss function is just a measure of "how far from right you are". 损失函数只是“您离正确有多远”的度量。

It's your model that will separate things, and the results you expect from your model are y_true . 分离事物的是您的模型,而您期望模型得到的结果是y_true

You should use a regular loss, with X_training = noisy images and Y_training = noises . 您应该使用常规损耗, X_training = noisy imagesY_training = noises


That said... 那个...

You can create a tensor for noisy_img outside the loss function and keep it stored. 您可以在损失函数之外为noisy_img创建一个张量并将其保存。 All operations inside a loss function must be tensor functions, so use the keras backend for that: 损失函数中的所有操作都必须是张量函数,因此请使用keras后端

import keras.backend as K

noisy_img = K.variable(X_training) #you must do this for each bach

But you must take batch sizes into account, this var being outside the loss function will need you to fit just one batch per epoch . 但是您必须考虑批次大小,该变量超出损失函数将需要您每个时期仅容纳一个批次

def loss(y_true,y_pred):
    return K.mean(K.square(y_pred-y_true) - K.square(y_true-noisy_img))

Training one batch per epoch: 每个时期训练一批:

for batch in range(0,totalSamples,size):
    noisy_img = K.variable(X_training[batch:size])
    model.fit(X_training[batch:size],Y_training[batch:size], batch_size=size)

For using just a mean squared error , organize your data like this: 为了仅使用均方误差 ,请按以下方式组织数据:

originalImages = loadYourImages() #without noises
Y_training = createRandomNoises() #without images

X_training = addNoiseToImages(originalImages,Y_training)

Now you just use a "mse", or any other built-in loss. 现在,您只需使用“ mse”或任何其他内置损失。

model.fit(X_training,Y_training,....)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM