BatchNorm(批量归一化)之所以可以“折叠”(Fold)到前一层(通常是卷积层 Conv 或线性层 Linear)中,根本原因在于它的统计参数是静态的(Static),且计算过程可以转化为线性变换。
1. BatchNorm 的计算公式
在推理阶段(Inference Mode),BatchNorm 的公式如下:
x^=x−μσ \hat{x} = \frac{x - \mu}{\sigma}x^=σx−μ
y=γx^+β y = \gamma \hat{x} + \betay=γx^+β
其中:
- xxx是输入数据。
- μ\muμ是均值,σ\sigmaσ是标准差。
- γ\gammaγ和β\betaβ是可学习的仿射参数。
2. 训练阶段 vs. 推理阶段
- 训练阶段:μ\muμ和σ\sigmaσ是基于当前 Mini-batch 的数据计算出来的,每个 batch 都不同。因此,无法预先确定这些值,也就无法合并。
PyTorch / TF 还会维护:
moving_mean(滑动均值)
moving_var(滑动方差)`
moving_mean = momentum * moving_mean + (1 - momentum) * mu_B moving_var = momentum * moving_var + (1 - momentum) * sigma_B^2- 推理阶段:μ\muμ和σ\sigmaσ使用的是在训练过程中通过“动量法”累计得到的全局统计量(Running Mean 和 Running Variance)。这些值是固定不变常量。推理阶段“也可以用 batch 统计”,但几乎从不这样做。**
3. 那推理时“用 batch 统计行不行?”
✅ 技术上:完全可以
⚠️ 但这是强烈不推荐的做法。
❌ 为什么不推荐?
1️⃣ batch 太小 → 统计极不可靠
| batch size | 问题 |
|---|---|
| 1 | 方差为 0,直接炸 |
| 2~8 | 噪声巨大 |
| ≥32 | 勉强稳定 |
推理时 batch 往往不可控。
2️⃣ 同一个样本,输出会变
同一张图片:
- 单独推理 → 一个结果
- 换一批一起推理 → 另一个结果
这在生产环境中是不可接受的 bug。
4. 数学推导:如何折叠?
由于μ,σ,γ,β\mu, \sigma, \gamma, \betaμ,σ,γ,β在推理时都是常数,我们可以将 BatchNorm 的步骤合并为一个单一的线性变换。
假设前一层(如卷积层)的输出是xxx,其计算过程为x=W⋅input+bx = W \cdot input + bx=W⋅input+b。
将 BatchNorm 公式展开:
y=γ(x−μσ)+β y = \gamma \left( \frac{x - \mu}{\sigma} \right) + \betay=γ(σx−μ)+β
y=(γσ)x−(γ⋅μσ)+β y = \left( \frac{\gamma}{\sigma} \right) x - \left( \frac{\gamma \cdot \mu}{\sigma} \right) + \betay=(σγ)x−(σγ⋅μ)+β
令:
- 新的权重W′=γσ⋅WW' = \frac{\gamma}{\sigma} \cdot WW′=σγ⋅W
- 新的偏置b′=γσ⋅b+β−γ⋅μσb' = \frac{\gamma}{\sigma} \cdot b + \beta - \frac{\gamma \cdot \mu}{\sigma}b′=σγ⋅b+β−σγ⋅μ
那么,整个 Conv + BatchNorm 的操作就可以简化为:
y=W′⋅input+b′ y = W' \cdot input + b'y=W′⋅input+b′
结论:BatchNorm 的操作被完全吸收进了卷积层的权重WWW和偏置bbb中。在推理时,不再需要单独执行 BatchNorm 层,从而减少了计算量内存访问。
5 为什么 LayerNorm 不能折叠?
这与LayerNorm在推理阶段的特性相反:
动态统计量:
LayerNorm 的均值μX\mu_XμX和标准差σX\sigma_XσX不是预训练好的固定值,而是在每一次前向传播时,根据当前输入样本XXX动态计算出来的。依赖当前输入:
公式如下:
μX=mean(X),σX=std(X) \mu_X = \text{mean}(X), \quad \sigma_X = \text{std}(X)μX=mean(X),σX=std(X)
因为μX\mu_XμX和σX\sigma_XσX依赖于XXX,而XXX又是前一层的输出,所以你不能在训练阶段或部署前预先计算出μX\mu_XμX和σX。\sigma_X。σX。非线性耦合:
由于σX\sigma_XσX在分母上,且它随输入变化,LayerNorm 引入了一个非线性的、输入依赖的缩放因子。这个因子无法像常数那样被提取出来合并到前一层权重中。
6 总结对比
| 特性 | BatchNorm | LayerNorm |
|---|---|---|
| 统计量来源 | 训练阶段累计的全局常量 (Running Stats) | 推理阶段根据当前输入实时计算 |
| 是否静态 | 是(Static) | 否(Dynamic/Per-sample) |
| 能否折叠 | 能(Conv + BN→\rightarrow→New Conv) | 不能(BN 依赖于当前输入XXX) |
| 原因 | μ,σ\mu, \sigmaμ,σ是常数,可合并进权重 | μ,σ\mu, \sigmaμ,σ是变量,随XXX变化 |
与 BatchNorm 不同,LayerNorm 由于其动态计算特性,无法折叠到前一层,因此我们必须单独对其进行量化。