Keras:自定义预处理作为计算图的一部分

时间:2019-05-25 20:24:36

标签: python tensorflow machine-learning keras

我目前正在研究一个回归问题,我需要以某种方式(原始操作无关紧要)对原始输入数据进行预处理,然后才能将其输入到神经网络中。我知道预处理通常是在模型外部进行的,但是由于我还需要网络wrt输出的渐变。原始输入数据(用于损失函数),我需要将预处理包含在计算图中。

从我收集的数据中,我需要将所得的张量作为神经网络的输入,以便在图中将这两个部分连接起来。一个重要的注意事项是,预处理是在整个训练集上完成的,这意味着只需进行一次即可。

我已经使用Keras后端函数成功实现了此功能,但是问题在于,预处理部分似乎是在模型的每次正向传递中执行的,这既不必要,又非常慢。我的希望是将输入张量视为网络的某些静态(但可微分)输入,在训练过程中向前和向后传播只是在网络输入和输出之间流动,但似乎并没有那样工作

由于我的代码很大而且很复杂,因此我将保留一个“半伪”代码,以简单地显示我要执行的操作的要点。

import tensorflow.keras.backend as K
from tensorflow.keras.layers import Input, Dense
from tensorflow.keras.models import Model

raw_data, target_data = load_data()
raw_tens = K.variable(raw_data)
out_tens = K.variable(target_data)

def preprocess(data_tens):
    input_tensor = ... # Preprocess the raw data using backend functions
    # Print statement to see when this operation is being performed
    input_tensor = K.print_tensor(input_tensor, message="Passed!")

    return input_tensor

in_tens = preprocess(raw_tens)

model_input = Input(tensor=in_tens)

# Define layers in the model
h = Dense(100, activation='tanh')(model_input)
...
output = Dense(1, activation='linear')(h)

# Define a custom loss function using the gradient wrt raw data
def custom_loss(y_true, y_pred):
    grad = K.gradients(y_pred, raw_tens)[0]

    loss = ... # some loss including the computed gradient
    return loss

# Define model and compile model using a custom loss function
model = Model(inputs=model_input, outputs=output)
model.compile(loss=custom_loss, optimizer='adam')

# Fit model
model.fit(y = out_tens, epochs = 1000, steps_per_epoch = 1)

在预处理函数中,我向张量添加了一个打印语句,该语句在调用该函数时就进行打印,并且确实在训练期间的每个时期都进行打印。即使我不在损失函数中包含渐变,也会发生这种情况,表明渐变很可能在正向传递中打印。但是,模型确实可以按照预期进行训练和预测,因此实现似乎是正确的。

我的逻辑/关于图形的工作原理可能存在一些缺陷,我希望有一个解决问题的简单方法。

总结:

  1. 我如何将“恒定”,可微分张量作为输入输入到神经网络,而在每次通过网络的正向传递过程中都无需重新计算张量?

由于预处理张量包含 all 个训练样本,因此我也想拆分和训练较小的批次,所以:

  1. 鉴于存在针对1.的解决方案,批量培训如何与此相结合?我是否必须创建一个适合fit_generator的生成器,还是可以让Keras使用fit处理它?<​​/ li>

希望问题已经很明显了,我感谢所有帮助/线索!

0 个答案:

没有答案