深度学习使计算机能够自动分析图像,例如从医学影像中分割肿瘤或器官。然而,不同数据集差异大、硬件条件不一,传统方法依赖专家手动设计网络和调参。
nnU-Net 实现了高度自动化,无需人工反复试错,可自动完成数据预处理、网络结构设计、训练策略及结果后处理,并针对每一个新任务自动调整。
Introduction
- 语义分割就是让电脑把医学影像里的不同结构'认出来并标出来',在很多地方都非常关键,是医学影像里非常核心的一项技术。
- 现在大多数医学影像分割都用深度学习,而且研究非常火(70%)。
- 现实问题是:① 想把一个分割模型'用好',非常依赖专家经验;② 一点点参数设置错了,效果就会大幅下降。
- 尤其在 3D 医学影像中差异很大,一个数据集调好的方案,几乎不能直接用到另一个,而且超参很多很复杂。
- 用 AutoML 需要机器多的训练次数,非常耗就算资源,实际上只能调一小部分,剩下的还是要人来决定,而且给新数据集用 AutoML,本身又需要专家来设搜索空间。
作者给出的思路:把专家经验系统化 + 规则化,只把少量事情留给数据来学,整个流程为:预处理→网络结构→训练→后处理,将模型参数分为以下三个部分:
- 永远不变的设置(fixed parameters):哪些设计在不同数据集之间通用直接固定,不再调。
- 看数据特征就能决定的(rule-based parameters):先提取数据指纹(比如图像大小、分辨率等),再用规则自动决定模型要怎么配。
- 实在没法规则化的才用数据学(empirical parameters):只剩很少一部分需要真正训练来决定。
nnUNet 具体自动化参数设计
整体的数据框架如下:

- Fixed Parameters:unet 架构、优化器、等。
- Data fingerprint:图像尺寸/像素体素间距/各类别占比等。
- Pipeline fingerprint:patch 大小/batch size/网络有多深等。
- Rule Parameters:比如:先把 patch 设成图像的中位大小,然后在不爆显存的前提下,一边缩小 patch,一边自动调整网络结构,直到能保证 batch size ≥ 2(网络的深度、pooling 等都会跟着一起自动修改)。
- Empirical:选哪个模型效果好,要不要做某种后处理。
应用到新数据集时:自动提取数据指纹→执行所有规则生成模型配置→默认训练三种模型(2D/全分辨 3D/二阶段 3D)→交叉验证选最优模型或模型组合→自动判断要不要加一个简单的后处理。
下面具体说说每一板块怎么工作的。
Fixed Parameters 具体设计
- 不搞复杂结构,U-Net 就够了。
- 网络模块里用最基础的组件:卷积 → Instance Normalization → Leaky ReLU,其中 Instance Normalization:自己和自己比,医学图像 batch 小同时差异大(CT 亮度不同)。
- 每个尺度固定用两个卷积块:编码器(每层两个连续卷积)和解码器(每层两个连续卷积)。
固定了每一层网络中的结构,所以后面 Rule 部分才能实现通过显存和 patch 调整网络深度。
- 下采样和上采样的方式也固定:下用带步长卷积,上用转置卷积(作者强调用不用 max pooling、双线性插值,其实对精度影响不大)。
- 为什么要用三种 UNet:作者承认很难提前知道哪种 U-Net 对哪个数据集最好,所以最后交叉验证自动选最好。
- 2D U-Net:在原始分辨率上逐帧做,适合层厚层间距差异大的,比如 MRI。
- 3D 全分辨:一般情况下效果最好,但是受限于显存可能 patch 较小,看不够上下文。
- 3D 级联:专门针对特别大的 3D 图像。
- 训练策略:1000 个 epoch,每个 epoch 迭代 250 次。
- 优化器:SGD 初始学习率 0.01,Momentum 0.99,学习率 polyLR 几乎线性降到 0(医学稳定)。
- 数据增强:必须有而且在线,训练时动态随机增强,每次看到的样本不一样是 SOTA 的关键之一,每次从磁盘读取 patch 都随机决定要不要做某种增强。
- 类别不平衡:医学图像常见目标小背景多,所以适当的过采样前景。训练前知道 GT,强制一定百分比的 patch 中心点位于前景。
- 损失函数:Dice(不平衡数据友好,patch 不稳定)+ 交叉熵(训练稳定)的取平均。
- 推理阶段:五折推理 ensemble(ensemble 就是在做五折概率分数平均),patch 推理。
- 防止拼接痕迹:patch 重叠一半,高斯权重(这个只在 cascade 里面会有用到)。
patch 重叠一半 + 高斯权重
patch1: [1 2 3 4 5 6 7 8] patch2: [5 6 7 8 9 10 11 12] patch3: [9 10 11 12 13 14 15 16] patch 权重(高斯形状): [0.1 0.3 0.6 0.9 0.9 0.6 0.3 0.1]
重叠一半首先保证一张图中间的位置被预测两次,其次高斯噪声保证能压住不准的预测,对于位置 8 来说 patch1 中属于边缘预测不准,所以权重小,在 patch2 中位于中间权重高。这是 1D 看起来红色区域的问题很严重,但是在大尺寸的医学图像中,nnU-Net 接受极少数'最外圈像素'的不完美,换取整体结构预测的稳定和高效,因为分割任务看中的是结构而不是边缘单点。
patch 中间预测准确边缘预测差
patch1 预测: [0.6 0.7 0.8 0.9 0.9 0.8 0.6 0.3] ← 边缘差 patch2 预测: [0.4 0.6 0.8 0.9 0.9 0.8 0.6 0.4] 拼接后 …… 0.3 | 0.4 …… ↑ 这里形成'接缝'
Rule Parameters 具体设计

动态网络调整保证网络看的全
- patch 数量决定下采样次数,下采样次数决定网络深度。
- 网络深度必须和 patch 大小匹配:patch 越大 → 网络需要越深。
- 下采样到特征图足够小为止:一直下采样,直到 feature map 至少变成 4×4(×4)。
- 网络深度由下采样次数决定:每下采样一次:encoder 多 2 个 conv;decoder 多 2 个 conv;加 1 个转置卷积。
- 深监督:在 decoder 的多个尺度都加 loss,但不在最底两级加(太粗糙)。
- 各向异性数据。
- 问题:层间距很大的话,3D 卷积会直接将不相关的层硬连接到一起。
- 解决:先只在平面内下采样(2D),目标 spacing 与重采样到下采样。
针对各向同性/异性数据集设计重采样策略
- 各向同性数据:每个轴用训练集 spacing 的中位数,图像三次样条插值,标签线性插值。
- 各向异性数据(层厚,重采样出现伪影):
- **二维下采样阶段:**首先在二维做下采样(每次下采样,有效 spacing 增加相应倍数),z 方向暂时不下采样。
- **Resampling 阶段:**out-of-plane 轴用 10% 分位 spacing(比中位数小)提高该方向分辨率,比如说 10% 分位是 4.5,那么就先重采样到 spacing=(0.8, 0.8, 4.5),减少极端各向异性带来的插值伪影。
- **In-Plane 下采样阶段:**然后 z 方向上不下采样,卷积核 size = 1 不跨 z 融合,一直在 in-plane 做下采样,直到 x/y 方向的感受野(物理尺度) ≈ z 方向 spacing,才逐步允许在 z 方向进行跨切片信息聚合(卷积核 > 1),是否在 z 方向下采样则取决于该轴的尺寸是否仍然足够大。
- 插值策略:在out-of-plane 轴图像和标签用最近邻插值,减少切片间的假结构,in-plane 上还是用的图像三次样条插值,标签线性插值。
举个例子
spacing = (0.8, 0.8, 5.0) mm shape = (224, 224, 32) 下采样一次 shape 变成(112,112,32)那么有效 spacing 下降到 1.6,逐渐和 xy 轴 spacing 趋近
特别的当医学图像特别大,导致 full-res patch 覆盖 < 12.5% 图像时触发 3D U-Net cascade(大图解决方案)。下面的图中能看到 full-res spacing 和 3D UNet Cascade 网络里面的 low resolution 情况下的目标 spacing 不一致。

具体操作是:首先 low-res spacing = full-res spacing 然后每一步把 spacing 增加 1%(image size 变小),同时重新计算重采样后的图像大小,patch size 等,直到 patch 覆盖的图像比例等于 25% 的图像中位尺寸。
Patch 大小动态确定
patch 要尽可能大(上下文信息多),但必须还能塞下 batch size ≥ 2)。
- patch 的长宽高比例跟重采样后训练数据的中位 shape 一致,训练之前会把数据重采样到某个 target spacing,例如重采样后,训练集里病例的 shape 可能是:
- case3: 176×160×88
- case2: 192×192×80
- case1: 160×160×96
- 中位数就是 176×160×88,所以 patch 就设置为 176×160×88,之后再整体缩小直到显存放得下,同时 batch≥2。Batch 大小≥2 就很稳定了,如果显存还有剩先把 patch 调大再把 batch 往上加,一直加到显存满。
不同数据强度归一化策略
- 默认规则:每例图单独做 Z-score(3 维的话就是 3D 整体),医学图像跨病人强度差异大。
- CT 特殊处理:CT 有 HU 值,用前景体素的轻度分布统一一个全局化归一方案。
- 前景强度的 0.5% 和 99.5% 分位数作为上下界,把更极端的值截掉,比如:x = min(max(x, -300), 500)。
- 再用同一批前景强度的全局 mean/std 做 z-score(同一批数据集,不是单个患者)。
Empirical 具体设计
- 虽然论文结果显示 3D full-resolution U-Net 整体上效果最好,但是对于具体的数据集没办法百分百预判,所以 nnunet 直接在每种配置下面做交叉验证,自动选择最佳模型或者多个模型的 ensemble。
- 后处理:只保留最大的连通区域(图像里只会有一个器官或病灶,但可能多预测出几个小碎块),只有当后处理后的 dice 有明显提升时才会做后处理,否则完全不做。
实验结果
公开数据集上性能 SOTA
作者在用大量、权威的实验来'证明 nnU-Net 不是只对一两个数据集好用,而是非常通用',并且效果好:
下面这个图中红点是 nnunet 的性能,在多个任务上都是 SOTA。

配置>架构的实验说明
方法配置中的细节比架构调整对性能的影响要大,作者以 KiTS 2019 挑战赛为例进行分析(当年 MICCAI 规模最大的比赛,非常具有代表性):

说明:排名前 15 的都是 unet like 网络架构,那些'流行结构改进'并不是成功的必要条件(残差、Dense……)。

冠军同款的 unet+ 残差网络架构也会出现排名分布差异,因为最关键的是他们的配置参数不同。
得到结论医学图像分割的模型配置,本质上是一个'高维、强耦合'的优化问题,在多个数据集上达到的新 SOTA 也说明,该现象不是个例而是**普遍规律:配置>架构。**另外,排行表里几乎没有 AutoML 方法(只有一个提到了用网格搜索调了少量参数,18/100),大多数方法反复调参,凭经验调 pipeline。
为什么依据数据配置参数不能开盒即用

为什么必须'因数据而异地自动配置',没有开盒即用的模型嘛。
- 不同数据在图形大小、体素间等差异很大。
- pipeline 的合适配置,往往直接或间接依赖于数据指纹,而且这种依赖关系非常复杂。
- 一个数据集上训练好的模型,换到另外一个模型上往往就不是最优。
nnunet 策略:① 找出 robust design decisions(跨数据集)② interdependencies(关键依赖关系)不是假设一套参数走天下,而是有规则变化。
为什么不推荐手动调参
作者强调 nnunet 是一个研究平台而不是方法,可以把新想法、新 loss 插进来,不需要手动调整参数。
作者考虑了一些常见的调参策略:
| 改动类型 | 含义 |
|---|---|
| 换 loss | Dice → Cross-Entropy / TopK |
| 加结构 | Encoder 加 residual |
| 网络更深 | 每层 3 个 conv(不是 2 个) |
| 换优化器 | SGD → Adam |
| 改优化器参数 | 减小 momentum |
| 换归一化 | InstanceNorm → BatchNorm |
| 去掉数据增强 | Ablation |
在验证集上用 bootstrap 生成 1000 个'虚拟验证集',在每个虚拟验证集上面给这 9 个方法排个名,分布靠左说明排名靠前,分布不宽说明波动不大很稳定。

得出结论:
- 同一个改动,在不同数据集上排名剧烈波动。
- 很多改动'看起来很强',但只对某些数据集有用。
- 但没有任何一个改动,在所有数据集上都稳定提升。
Discussion
nnU-Net 并不是靠新技术取胜,而是通过系统化专家经验,在大量不同医学分割任务中实现了稳定、强泛化的性能;同时它暴露了当前研究中评测不足、baseline 不公平等问题,并为未来医学分割研究提供了一个统一、可靠、可扩展的基础工具。

