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

Keras深度学习:预测输出与输入栅格形状不符问题求助

问题:Keras模型推理输出形状不符合预期

我使用Keras训练深度学习模型,训练数据为125x125像素的3D RGB数组。推理阶段给输入添加批量维度后(输入形状变为(1,128,128,3))脚本可运行,但输出形状完全错误,当前输出为TensorShape([1,4096,2]),该形状与模型最后两层输出一致。附上相关信息,寻求解决方法:

模型结构信息

model.summary()
Model: "model_13"
__________________________________________________________________________________________________
 Layer (type)                    Output Shape         Param #  Connected to
==================================================================================================
 input_4 (InputLayer)            [(None, 128, 128, 3  0        []
                                 )]

 block1_conv1 (Conv2D)           (None, 128, 128, 64  1792     ['input_4[0][0]']
                                 )

 block1_conv2 (Conv2D)           (None, 128, 128, 64  36928    ['block1_conv1[0][0]']
                                 )

 block1_pool (MaxPooling2D)      (None, 64, 64, 64)   0        ['block1_conv2[0][0]']

 block2_conv1 (Conv2D)           (None, 64, 64, 128)  73856    ['block1_pool[0][0]']

 block2_conv2 (Conv2D)           (None, 64, 64, 128)  147584   ['block2_conv1[0][0]']

 block2_pool (MaxPooling2D)      (None, 32, 32, 128)  0        ['block2_conv2[0][0]']

 block3_conv1 (Conv2D)           (None, 32, 32, 256)  295168   ['block2_pool[0][0]']

 block3_conv2 (Conv2D)           (None, 32, 32, 256)  590080   ['block3_conv1[0][0]']

 block3_conv3 (Conv2D)           (None, 32, 32, 256)  590080   ['block3_conv2[0][0]']

 block3_pool (MaxPooling2D)      (None, 16, 16, 256)  0        ['block3_conv3[0][0]']

 block4_conv1 (Conv2D)           (None, 16, 16, 512)  1180160  ['block3_pool[0][0]']

 block4_conv2 (Conv2D)           (None, 16, 16, 512)  2359808  ['block4_conv1[0][0]']

 block4_conv3 (Conv2D)           (None, 16, 16, 512)  2359808  ['block4_conv2[0][0]']

 block4_pool (MaxPooling2D)      (None, 8, 8, 512)    0        ['block4_conv3[0][0]']

 zero_padding2d_4 (ZeroPadding2  (None, 10, 10, 512)  0        ['block4_pool[0][0]']
 D)

 conv2d_27 (Conv2D)              (None, 8, 8, 512)    2359808  ['zero_padding2d_4[0][0]']

 batch_normalization_4 (BatchNo  (None, 8, 8, 512)    2048     ['conv2d_27[0][0]']
 rmalization)

 up_sampling2d_7 (UpSampling2D)  (None, 16, 16, 512)  0        ['batch_normalization_4[0][0]']

 concatenate_7 (Concatenate)     (None, 16, 16, 768)  0        ['up_sampling2d_7[0][0]',
                                                               'block3_pool[0][0]']

 zero_padding2d_5 (ZeroPadding2  (None, 18, 18, 768)  0        ['concatenate_7[0][0]']
 D)

 conv2d_28 (Conv2D)              (None, 16, 16, 256)  1769728  ['zero_padding2d_5[0][0]']

 batch_normalization_5 (BatchNo  (None, 16, 16, 256)  1024     ['conv2d_28[0][0]']
 rmalization)

 up_sampling2d_8 (UpSampling2D)  (None, 32, 32, 256)  0        ['batch_normalization_5[0][0]']

 concatenate_8 (Concatenate)     (None, 32, 32, 384)  0        ['up_sampling2d_8[0][0]',
                                                               'block2_pool[0][0]']

 zero_padding2d_6 (ZeroPadding2  (None, 34, 34, 384)  0        ['concatenate_8[0][0]']
 D)

 conv2d_29 (Conv2D)              (None, 32, 32, 128)  442496   ['zero_padding2d_6[0][0]']

 batch_normalization_6 (BatchNo  (None, 32, 32, 128)  512      ['conv2d_29[0][0]']
 rmalization)

 up_sampling2d_9 (UpSampling2D)  (None, 64, 64, 128)  0        ['batch_normalization_6[0][0]']

 concatenate_9 (Concatenate)     (None, 64, 64, 192)  0        ['up_sampling2d_9[0][0]',
                                                               'block1_pool[0][0]']

 zero_padding2d_7 (ZeroPadding2  (None, 66, 66, 192)  0        ['concatenate_9[0][0]']
 D)

 conv2d_30 (Conv2D)              (None, 64, 64, 64)   110656   ['zero_padding2d_7[0][0]']

 batch_normalization_7 (BatchNo  (None, 64, 64, 64)   256      ['conv2d_30[0][0]']
 rmalization)

 conv2d_31 (Conv2D)              (None, 64, 64, 2)    1154     ['batch_normalization_7[0][0]']

 reshape_3 (Reshape)             (None, 4096, 2)      0        ['conv2d_31[0][0]']

 activation_3 (Activation)       (None, 4096, 2)      0        ['reshape_3[0][0]']

==================================================================================================
Total params: 12,322,946
Trainable params: 12,321,026
Non-trainable params: 1,920
__________________________________________________________________________________________________

model.inputs
Out[52]: [<KerasTensor: shape=(None, 128, 128, 3) dtype=float32 (created by layer 'input_4')>]

输入输出形状信息

val_data.shape
Out[53]: (1, 128, 128, 3)

out.shape
Out[54]: TensorShape([1, 4096, 2])

解决方法

问题根源

从模型结构可以看到:

  • 模型最后一个卷积层conv2d_31输出形状是(None,64,64,2),之后的reshape_3层把64x64的空间维度展平成了4096(64*64),得到(None,4096,2),这就是当前输出形状的来源。
  • 你的任务应该是需要输出和输入同尺寸的特征图(比如(1,128,128,2)),但当前模型的上采样路径只恢复到了64x64,还额外做了不必要的Reshape操作。

修复步骤

  • 移除Reshape和后置激活层:如果是语义分割类任务,不需要展平空间维度,直接删除reshape_3和activation_3层,把激活函数移到conv2d_31层(比如定义时用Conv2D(2, ..., activation='sigmoid'))。
  • 补充上采样到输入尺寸:当前模型最后一次上采样后是64x64,离输入的128x128还差一次2倍上采样。在batch_normalization_7之后添加UpSampling2D(size=(2,2))层,然后再接输出卷积层,确保输出空间尺寸和输入一致。示例代码:
    # 修改模型末尾部分
    x = layers.UpSampling2D(size=(2,2))(batch_normalization_7.output)
    x = layers.Conv2D(2, (3,3), padding='same', activation='softmax')(x)  # 根据任务选激活函数
    model = Model(inputs=input_4, outputs=x)
    
  • 对齐训练与推理数据尺寸:训练数据是125x125,但模型输入是128x128,训练时肯定做了resize操作,推理时也要保证输入先resize到128x128,避免尺寸不匹配问题。
  • 验证模型结构:修改后重新打印model.summary(),确认输出形状为(None,128,128,2),再用测试输入验证输出形状是否符合预期。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.09 11:40:35