Keras训练每隔一个epoch所有日志指标均为0问题求助
解决Keras训练每隔一个epoch指标全为0的问题
核心原因
你手动指定了steps_per_epoch=90和validation_steps=10,但ImageDataGenerator的生成器是状态化的——第一个epoch结束后,生成器的内部指针已指向训练数据末尾。第二个epoch时,生成器未自动重置,导致指定步数内未读取到有效样本,因此loss、accuracy等指标全部为0,训练时间也几乎为0。
修复方案
方案1:移除固定步数参数(推荐)
Keras可自动根据生成器的总样本数和batch_size计算每个epoch的步数,无需手动指定。修改model.fit()代码如下:
history1=model1.fit( train_generator_CD, validation_data = test_generator_CD, epochs = 20, callbacks=[myCallback()] )
方案2:手动重置生成器状态
如果必须保留固定步数,可自定义回调函数在每个epoch开始前重置生成器状态:
class ResetGeneratorCallback(keras.callbacks.Callback): def on_epoch_begin(self, epoch, logs=None): train_generator_CD.reset() test_generator_CD.reset() history1=model1.fit( train_generator_CD, validation_data = test_generator_CD, epochs = 20, steps_per_epoch = 90, validation_steps = 10, callbacks=[myCallback(), ResetGeneratorCallback()] )
补充说明
你的训练数据集有22500张图(25000的90%),batch_size=250,22500/250=90,所以steps_per_epoch=90的数值是正确的,但生成器不会自动重置指针,才导致偶数epoch无数据可读。移除手动步数参数后,Keras会在每个epoch结束后自动重置生成器,彻底避免这个问题。
原始异常日志
Epoch 1/20 90/90 ━━━━━━━━━━━━━━━━━━━━ 170s 2s/step - accuracy: 0.9974 - loss: 0.4769 - val_accuracy: 0.7968 - val_loss: 0.9699 Epoch 2/20 90/90 ━━━━━━━━━━━━━━━━━━━━ 0s 1ms/step - accuracy: 0.0000e+00 - loss: 0.0000e+00 - val_accuracy: 0.0000e+00 - val_loss: 0.0000e+00 Epoch 3/20 90/90 ━━━━━━━━━━━━━━━━━━━━ 175s 2s/step - accuracy: 0.9988 - loss: 0.4260 - val_accuracy: 0.8052 - val_loss: 0.9283 Epoch 4/20 90/90 ━━━━━━━━━━━━━━━━━━━━ 0s 728us/step - accuracy: 0.0000e+00 - loss: 0.0000e+00 - val_accuracy: 0.0000e+00 - val_loss: 0.0000e+00 etc...
原始模型代码
model1 = keras.models.Sequential([ keras.layers.Conv2D(16,(3,3), activation='relu', input_shape=(150, 150, 3)), keras.layers.MaxPooling2D(2,2), keras.layers.BatchNormalization(), keras.layers.Conv2D(32,(3,3), activation='relu'), keras.layers.MaxPooling2D(2,2), keras.layers.BatchNormalization(), keras.layers.Conv2D(64,(3,3), activation='relu'), keras.layers.MaxPooling2D(2,2), keras.layers.BatchNormalization(), keras.layers.Flatten(), keras.layers.Dense(512, activation='relu', kernel_regularizer=regularizers.l2(0.001)), keras.layers.Dropout(0.2), keras.layers.Dense(1, activation='sigmoid') ]) model1.compile(optimizer=Adam(learning_rate=0.0002), loss='binary_crossentropy', metrics=['accuracy']) train_CD = ImageDataGenerator(rescale=1.0/255.) train_generator_CD = train_CD.flow_from_directory( './images/cat_dog/train_data/', target_size = (150, 150), batch_size = 250, class_mode = 'binary') test_CD = ImageDataGenerator(rescale=1.0/255.) test_generator_CD = test_CD.flow_from_directory( './images/cat_dog/test_data/', target_size = (150, 150), batch_size = 250, class_mode = 'binary') history1=model1.fit( train_generator_CD, validation_data = test_generator_CD, epochs = 20, steps_per_epoch = 90, validation_steps = 10, callbacks=[myCallback()] )
内容的提问来源于stack exchange,提问作者Arden McArthur
相关产品推荐
相关产品推荐

