You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Keras二分类训练报logits与labels形状不匹配问题咨询

故障背景

我已检索过同类问题,但相关问题下的已采纳解决方案均无法解决我遇到的故障。
以下是编写二分类器的完整代码:

from google.colab import drive
drive.mount('/content/drive')

df = pd.read_csv('/content/drive/My Drive/dielectron.csv')
df = df.drop('Run', axis=1); df = df.drop('M', axis=1)
df.info()
df.head()

scaler = MinMaxScaler()

index = df.index.to_list() 
columns = df.columns.tolist()

scaler = MinMaxScaler()

df_scaled = scaler.fit_transform(df)
Df = pd.DataFrame(df_scaled , index=index , columns=columns)
Df.info()

Df= Df.drop('Event', axis=1)
x = Df.drop('Q2', axis=1).to_numpy()
y = Df['Q2']
y = np.asarray(y).astype('float32').reshape((-1,1))

model = tf.keras.Sequential([
                                   tf.keras.layers.Dense(16, activation='relu'),
                                   tf.keras.layers.Dense(16, activation='relu'),
                                   tf.keras.layers.Dense(16, activation='sigmoid')
])

epochs = 20


es = tf.keras.callbacks.EarlyStopping(monitor='val loss',
                                      patience = 3,
                                      mode = 'min',
                                      restore_best_weights=True)

model.compile(loss= tf.keras.losses.BinaryCrossentropy(),
              optimizer= tf.optimizers.Adam(),
              metrics= [tf.keras.metrics.BinaryAccuracy()]
)

history = model.fit(x, y, epochs=epochs, validation_split=0.3, callbacks=[es])

传入model.fit()的张量形状查询结果:

x.shape:(100000, 15)
y.shape:(100000, 1)

运行代码触发的报错核心信息:

ValueError: `logits` and `labels` must have the same shape, received ((None, 16) vs (None, 1)).

注:本人接触机器学习、深度学习与TensorFlow Keras时间较短,不排除代码存在低级错误。本次使用的为CERN电子碰撞公开数据集,同时需要明确logit的准确定义,此前查阅的资料解释存在冲突。

故障原因
  • 核心错误:二分类任务的输出层维度设置错误。标签y是单维度(每个样本对应一个0/1分类值),但模型最后一层设置了16个神经元,输出形状为(None,16),和标签的(None,1)形状不匹配,计算二元交叉熵损失时无法对齐维度直接报错。
  • 次要错误:早停回调的监控参数名书写错误,Keras中验证集损失的参数名为val_loss,代码中写的val loss带空格,会导致早停机制无法找到对应监控值。
  • 隐含错误:代码缺少必要的依赖导入,直接运行会触发NameError。
修复方法

按以下步骤修改代码即可正常运行:

  1. 在代码最开头补充缺失的依赖导入:
    import pandas as pd
    import numpy as np
    import tensorflow as tf
    from sklearn.preprocessing import MinMaxScaler
    
  2. 修改模型最后一层的神经元数量为1,匹配二分类单输出的要求:
    model = tf.keras.Sequential([
        tf.keras.layers.Dense(16, activation='relu'),
        tf.keras.layers.Dense(16, activation='relu'),
        tf.keras.layers.Dense(1, activation='sigmoid') # 原代码此处为16,改为1
    ])
    
  3. 修正早停回调的监控参数名,补全下划线:
    es = tf.keras.callbacks.EarlyStopping(monitor='val_loss', # 原代码此处为val loss,补上下划线
                                          patience = 3,
                                          mode = 'min',
                                          restore_best_weights=True)
    
logit 定义说明

logit是神经网络输出层未经过激活函数转换的原始输出值,值域为全体实数,没有被映射到概率区间。
以二分类场景为例:

  • 如果最后一层写Dense(1)(不指定激活函数),这一层直接输出的原始值就是logit;
  • 如果写Dense(1, activation='sigmoid'),框架会先输出1维logit,再经过sigmoid函数把值压缩到0~1区间,输出最终的分类概率。
    本次报错信息中提到的logits,就是模型最后一层输出的原始计算结果,因为最后一层设了16个神经元,所以输出16维logit,和1维的标签形状无法匹配,才触发了维度错误。

内容的提问来源于stack exchange,提问作者python newbie

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 10:27:29