TensorFlow Keras调用model.fit报Graph execution error求助
问题概述
基于tensorflow.keras搭建全连接神经网络,封装了批量遍历优化器、激活函数的训练函数,用于筛选最优训练配置:
- 输入特征
x_train为56列的pandas DataFrame - 标签
y_train为2列的pandas DataFrame
代码此前可正常运行,某日突然抛出Graph execution error,先后在MacOS、Ubuntu两台设备,Python3.9、Python3.10环境,启用/禁用GPU、重装TensorFlow等场景下测试,问题均复现,初步排除输入维度不匹配、环境配置问题。
复现代码
import ccxt import pandas as pd import numpy as np import tensorflow as tf import time import math import csv from sklearn.model_selection import train_test_split x_train, x_test, y_train, y_test = train_test_split(data_4candles, data_minmax) x_test, x_val, y_test, y_val = train_test_split(x_test, y_test) def model_compile_fit_predict(optimizer,activation,epochs,filepath): model = tf.keras.models.Sequential() model.add(tf.keras.layers.Dense(56, input_dim = 56, activation = activation)) model.add(tf.keras.layers.Dense(56, activation = activation)) model.add(tf.keras.layers.Dense(10, activation = activation)) model.add(tf.keras.layers.Dense(2, activation = activation)) model.compile(loss = 'mse', optimizer = optimizer, metrics = ['accuracy',tf.keras.metrics.Precision(),tf.keras.metrics.Recall()]) hist = model.fit(x_train, y_train, epochs = epochs, validation_data = (x_val, y_val)) loss, accuracy, precision, recall_1 = model.evaluate(x_test, y_test) hist_acc = hist.history['accuracy'] hist_loss = hist.history['loss'] hist_val_acc = hist.history['val_accuracy'] hist_val_loss = hist.history['val_loss'] model.save(filepath = filepath) output = [activation, optimizer, 'test accuracy and loss: ', accuracy, loss, 'true positive / (true positive + false positive): ', precision, 'true positive / (true positive + false negative): ', recall_1, 'train epoch accuracy and loss: ',hist_acc,hist_loss, 'validation epoch accuracy and loss: ', hist_val_acc,hist_val_loss] return output activation_functions = ['relu', 'softplus', 'selu', 'elu'] optimizers = ['RMSprop', 'Adam', 'Adadelta', 'Adagrad', 'Adamax', 'Nadam', 'Ftrl'] dummy_list1 = list() for i in optimizers: dummy_list2 = list() for j in activation_functions: output = model_compile_fit_predict(i,j,epochs=5,filepath = '/home/bae/MidasProject/ML/ML_file/'+i+'_'+j) dummy_list2.append(output) dummy_list1.append(dummy_list2) output_2d = dummy_list1
核心报错信息
报错栈最终定位到指标计算环节的断言失败:
Node: 'assert_less_equal/Assert/AssertGuard/Assert'
assertion failed: [predictions must be <= 1] [Condition x <= y did not hold element-wise:] [x (sequential/dense_3/Relu:0) = ] [[27222.8672 37717.7305][41931.543...]...] [y (Cast_7/x:0) = ] [1]
即模型输出层的预测值出现了万级别的远大于1的数值,触发了内置的输入合法性校验。
错误原因
- 代码中使用的
accuracy、Precision、Recall均为分类任务专属指标,这类指标要求输入的预测值必须落在[0,1]区间(代表样本属于对应类别的概率),但当前模型用mse作为损失,属于回归任务配置,逻辑本身不匹配。 - 遍历激活函数时,输出层也直接套用了relu、selu、elu等无输出上界的激活函数,这类激活的输出可以到任意大的正数值,完全不满足分类指标的输入要求,直接触发校验报错。
- 此前代码能运行,大概率是旧版本Keras未新增这层预测值范围的强校验,或是之前输出层单独配置了适配任务的激活函数,修改批量遍历逻辑时误将输出层激活也纳入遍历参数,导致问题突然出现。
修复方案
- 先明确任务类型,匹配对应配置:
- 如果是回归任务(和当前使用的MSE损失匹配):删除
accuracy、Precision、Recall三个分类指标,替换为MAE等回归任务指标;输出层不要套用遍历的激活函数,使用默认的线性激活即可。 - 如果是分类任务:将损失函数替换为对应交叉熵损失,输出层改用sigmoid/softmax等能将输出压缩到[0,1]区间的激活函数,同时确认标签格式符合分类任务要求后,再保留分类指标。
- 如果是回归任务(和当前使用的MSE损失匹配):删除
- 调整遍历逻辑:隐藏层激活可以放入列表遍历选优,但输出层激活必须和任务类型绑定,不能纳入遍历范围。
- 前置检查标签范围:如果做归一化后的回归任务,确认标签
data_minmax的缩放范围是否符合预期,若标签本身存在大于1的数值,绝对不能使用分类指标。
回归场景下的模型搭建核心修正代码参考:
def model_compile_fit_predict(optimizer,activation,epochs,filepath): model = tf.keras.models.Sequential() # 隐藏层沿用遍历的激活函数 model.add(tf.keras.layers.Dense(56, input_dim = 56, activation = activation)) model.add(tf.keras.layers.Dense(56, activation = activation)) model.add(tf.keras.layers.Dense(10, activation = activation)) # 输出层使用线性激活,不套用遍历参数 model.add(tf.keras.layers.Dense(2)) # 编译时使用匹配回归任务的指标 model.compile(loss = 'mse', optimizer = optimizer, metrics = ['mae']) # 后续训练、保存逻辑不变
内容的提问来源于stack exchange,提问作者BAE_Sangmin
相关产品推荐
相关产品推荐

