我注意到我在Keras开发的CNN模型有一些不稳定的行为,最终我发现这是随机种子的函数。根据种子的不同,我要么得到一些培训,要么不适应,要么不学习,不适应培训数据。
有关建模的更多详细信息: “图像”不是真实图像,而是自定义数据集的计算转换。 CNN是一个类似于小型Inception的体系结构。输出为回归,因此我最后使用了自定义缩放的S型激活函数。
我的图像已经过预先计算和增强,因此我编写了自己的小批处理生成器以随机顺序浏览这些图像。我想知道这是否与问题有关,但是从我的基本调试(打印返回的图像索引)来看,我看不到任何明显错误的地方。
Environment:
OS: Ubuntu 18.04.2 LTS
Python: 3.7.3
Keras: 2.2.4
Tensorflow: 1.13.1
## custom batch generator
def generate_batches(x, y, batch_size, shuffle=True):
data_size = x.shape[0]
indices = np.array(range(0, data_size))
while True:
if (shuffle == True):
np.random.shuffle(indices)
for start in range(0, data_size, batch_size):
end = start + min(batch_size, data_size - start)
batch_features = x[indices[start:end], :, :, :]
batch_values = y[indices[start:end]]
yield batch_features, batch_values
## return a value in the range of (3.0, 9.5)
def scaledSigmoid(x):
return (K.sigmoid(x) * (9.5 - 3.0)) + 3.0
# for debugging:
np.random.seed(1)
rn.seed(1)
tf.set_random_seed(1)
# Training data shape: (23670, 70, 70, 4)
# Testing data shape: (250, 70, 70, 4)
## initialize the output bias to the mean of the training Y value
mean_y_train = np.mean(Y_train)
bias_init = keras.initializers.Constant(value=mean_y_train)
## set up the model
input_shape = X_train.shape[1:]
input_img = Input(shape=input_shape)
steps_per_epoch = ceil(len(Y_train)/batch_size)
reduce_lr = ReduceLROnPlateau(monitor='val_loss', factor=0.5, patience=5, min_lr=1e-6, verbose=0)
generator = generate_batches(X_train, Y_train, batch_size, shuffle=True)
# 'get_model_for_params' is not shown here
model = get_model_for_params(input_img, bias_init, dpr, d1, d2, lrate)
# run the model
history = model.fit_generator(generator,
steps_per_epoch=steps_per_epoch,
epochs=epochs,
validation_data=(X_test, Y_test),
callbacks=[reduce_lr],
verbose=1)
我在这里附上两组情节。绘制学习历史记录(损失/时期)表明,随着随机种子1、3和4的出现,我看到随着时间的推移学习(不是很好,但现在已经足够好了),但是在第一次学习之后随机出现了种子2、5和6。最初的下降(偏差调整?)是没有学习的。绘制预测回归值与实际回归值可以得出种子1、3和4的确定拟合。但是,对于种子2、5和6,预测值都等于我缩放的乙状结肠激活函数的最小值。