当前位置: 首页 > news >正文

从 UNet 到 UCTransNet:一次分割项目中 BCE Loss 失效的踩坑记录

1. 问题背景

最近在做医学图像分割任务,目标是对 CT 图像进行前景/背景的二值分割。
在基线实验里,我使用 UNet + BCE 损失函数,训练和验证都能正常收敛,Dice 系数逐步提升,结果符合预期。

但当我尝试使用一些更复杂的网络(比如 UCTransNetTransFuse)时,情况完全变了:

  • 训练 loss 一直稳定在 0.693 左右(BCE 初始值);

  • Dice、IoU 等指标几乎始终为 0;

  • 输出的预测 mask 基本全是背景。


2. 调试过程

Step 1: 检查输入输出形状

在训练循环里打印数据和预测的形状:

print("x:", x.shape, "y:", y.shape, "pred:", outputs.shape)

确认输入图像和标签形状正常,模型输出 (B,1,H,W) 也没问题。

Step 2: 打印输出范围

outputs = model(x) 后面加:

print("outputs range:", outputs.min().item(), outputs.max().item())

结果发现:

outputs range: 0.0 ~ 1e-6

也就是说,模型的输出几乎都被限制在 0 附近且非负


3. 原因分析

这里的核心问题是 模型最后一层处理方式不当

  • 在 UNet 中,最后一层通常是一个 卷积层(Conv2d)直接输出 logits

  • 在 UCTransNet / TransFuse 的部分实现里,最后一层被加上了 ReLU 或 Sigmoid

为什么这会导致训练失败?

  1. BCEWithLogitsLoss 的需求

    • 它需要输入的是 原始 logits(可正可负)。

    • 内部会自动做 Sigmoid,把 logits 转成概率。

  2. 被 ReLU 截断的情况

    • 如果最后用了 ReLU,logits 就只能 ≥0。

    • 那么 Sigmoid 的最小值就是 0.5,模型没法表达「这是背景」。

    • 损失长期停在 0.693,指标始终为 0。

  3. 重复 Sigmoid 的情况

    • 如果最后手动加了 Sigmoid,然后再喂给 BCEWithLogitsLoss,就相当于 双重 Sigmoid,数值会被压缩,训练同样不收敛。


4. 解决方案

✅ 正确做法

  • 确认模型最后一层是 线性卷积层 (Conv2d),不要加 ReLU / Sigmoid。

  • 使用 BCEWithLogitsLoss 时,直接传 logits,不要自己再做 Sigmoid。

  • 计算指标(Dice、IoU)时,再手动对 logits 做一次 Sigmoid + 阈值化。

http://www.dtcms.com/a/394596.html

相关文章:

  • leetcode刷题记录2(java)
  • JAVA八股文——方法区
  • 链表操作与反转
  • AI编程 -- 学习笔记
  • 动态规划问题 -- 子数组模型(乘积最大数组)
  • 【AIGC】大模型面试高频考点18-大模型压力测试指标
  • Cannot find a valid baseurl for repo: base/7/x86_64
  • Lowpoly建模练习集
  • 六、kubernetes 1.29 之 Pod 控制器02
  • OpenCV:人脸检测,Haar 级联分类器原理
  • 类和对象 (上)
  • FreeRTOS 队列集(Queue Set)机制详解
  • 【论文速递】2025年第20周(May-11-17)(Robotics/Embodied AI/LLM)
  • 【秋招笔试】2025.09.21网易秋招笔试真题
  • C++ 之 【特殊类设计 与 类型转换】
  • 第14章 MySQL索引
  • Entities - 遍历与查询
  • TargetGroup 全面优化:从六个维度打造卓越用户体验
  • Proxy与Reflect
  • 浅解Letterbox算法
  • 【Triton 教程】triton_language.permute
  • JavaScript洗牌算法实践
  • 掌握timedatectl命令:Ubuntu 系统时间管理指南
  • 【RT Thread】RTT内核对象机制详解
  • Seata分布式事务
  • 用例图讲解
  • makefile原理
  • AUTOSAR CP开发流程总结
  • 通过VNC实现树莓派远程桌面访问
  • linux信号done