我在进行5折交叉验证。然后我为每个分割绘制了损失和验证损失随epoch的变化图。
我发现这个图表令人不安。
- 只有第一个看起来对我来说是“正常”的
- 我发现损失水平非常非常低
- 我不明白为什么验证损失总是低于训练损失(图表4和5)。
我的交叉验证方法:
def cv(X, y, model, n_splits=5, epochs=5, batch_size=1024, random_state=42, verbose=0): # kf = KFold(n_splits=n_splits, shuffle=True, random_state=random_state) kf = KFold(n_splits=n_splits, shuffle=False, random_state=random_state) histories = [] for s in kf.split(X): X_train = X.iloc[s[0]].to_numpy() y_train = y.iloc[s[0]]['Target'].to_numpy() X_test = X.iloc[s[1]].to_numpy() y_test = y.iloc[s[1]]['Target'].to_numpy() h = model.fit(X_train, y_train, epochs=epochs, batch_size=batch_size, validation_data=(X_test, y_test), verbose=verbose) histories.append(h) return histories
模型:
def model_8(input_dim) -> tf.keras.models: get_custom_objects().update({'swish': Activation(swish)}) inputs = Input(shape=(input_dim,)) x = Dense(200, activation='swish', name='hl_1')(inputs) x = Dense(200, activation='swish', name='hl_2')(x) x = Dense(200, activation='swish', name='hl_3')(x) x = Dense(200, activation='swish', name='hl_4')(x) x = Dense(200, activation='swish', name='hl_5')(x) x = Dense(200, activation='swish', name='hl_6')(x) x = Dense(200, activation='swish', name='hl_7')(x) x = Dense(200, activation='swish', name='hl_8')(x) x = Dense(200, activation='swish', name='hl_9')(x) x = Dense(200, activation='swish', name='hl_10')(x) x = Dense(200, activation='swish', name='hl_11')(x) output = Dense(1, activation='sigmoid', name='output')(x) model = Model(inputs=inputs, outputs=output) model.compile(loss='mean_squared_error', optimizer='adam') #model._name = function.__name__ model._name = inspect.stack()[0][3] return model
绘图函数:
def plots_(models_cv_histories, n_splits, save=False): """绘制每个训练模型的所有学习曲线 参数: models_cv_histories {array} -- 历史记录数组 """ nb_models = len(models_cv_histories) fig, axes = plt.subplots(nrows=nb_models, ncols=n_splits, figsize=(12, 5)) row_index = 0 for cv_model in models_cv_histories: hist = cv_model[1] epochs = range(1, len(hist[0].epoch) + 1) col_index = 0 for split_ in hist: loss = split_.history['loss'] epochs = split_.epoch val_loss = split_.history['val_loss'] model_name = split_.model.name if nb_models > 1: ax = axes[row_index][col_index] else: ax = axes[col_index] ax.set_title(model_name + ' 分割 ' + str(col_index)) ax.plot(epochs, loss, color="r", label="损失") ax.plot(epochs, val_loss, color="g", label="验证损失") ax.set_xlabel("epochs") ax.xaxis.set_major_locator(MaxNLocator(integer=True)) ax.set_ylabel("损失") ax.legend(loc="upper right") col_index += 1 row_index += 1 fig.subplots_adjust() if save: plt.savefig("plots/test.png") fig.tight_layout() plt.show()
你能给我一些提示吗?
回答:
我在这里找到了答案这里。每次分割后,fit函数会继续训练。我应该在每次分割后刷新模型。