vanishing / exploding gradient 是怎么来的?
怎么解决?
先弄清楚:每个概念是什么
- Backpropagation 与 chain rule
- loss 的 gradient 从最后一层往前传,每经过一层就乘上这一层的倍率。
- Jacobian
- 一层的倍率表,输入每个分量动一点,输出每个分量跟着动多少。标量时就是导数。例:\(h = 3x\) 的 Jacobian 是 3;\(h = \sigma(z)\) 的是 \(\sigma'(z)\)。
- Vanishing / exploding gradient
- 倍率小于 1,连乘后指数变小,前几层几乎收不到 gradient。倍率大于 1 则指数变大,一步跨太远,loss 变成 NaN。例:10 层,每层 0.5 → \(0.5^{10} \approx 0.001\);每层 1.5 → \(1.5^{10} \approx 57.7\)。
- Saturation
- sigmoid 两头是平的,导数接近 0,详见 activation function。
- Residual connection
- 在每层旁边修一条直达通道,输出 = \(x + F(x)\)。就算 \(F\) 那条路倍率很小,gradient 也能沿 \(x\) 这条路原样传回去。
30 秒回答
Backprop computes early-layer gradients as a product of per-layer Jacobians. If their norms are below one, the gradient shrinks exponentially with depth and early layers stop learning; above one, it explodes and the loss becomes NaN. Sigmoid makes it worse, since its derivative is at most 0.25, and RNNs are the worst case because they multiply by the same matrix at every step. Fixes: ReLU, whose derivative is 1 for positive inputs; Xavier or He initialization; BatchNorm or LayerNorm; residual connections that add an identity path; gradient clipping for exploding gradients; and LSTM or GRU, whose additive cell state avoids the repeated multiplication.
推导 / 关键公式
gradient = 各层 Jacobian 连乘
第 \(l\) 层 \(h_l = f(W_l h_{l-1})\),Jacobian 是 \(\operatorname{diag}(f')\,W_l\)。chain rule:
\[ \frac{\partial L}{\partial h_0} = \frac{\partial L}{\partial h_L}\cdot\frac{\partial h_L}{\partial h_{L-1}}\cdots\frac{\partial h_1}{\partial h_0} \]每个 Jacobian 的 norm 约为 \(a\) 时,gradient 缩放 \(a^L\) 倍:\(a < 1\) → vanishing,\(a > 1\) → exploding。
sigmoid 与 RNN 为什么更糟
\[ \sigma'(z) = \sigma(z)\big(1 - \sigma(z)\big) \le \tfrac14 \]每过一层至少乘一个 ≤ 1/4 的数,saturate 时接近 0。RNN 每步乘同一个 \(W\),gradient 按 \(\lambda^T\) 缩放(\(\lambda\) 是 \(W\) 的 eigenvalue)。
residual 和 LSTM:把乘法换成加法
\[ \frac{\partial}{\partial h}\big(h + F(h)\big) = I + \frac{\partial F}{\partial h} \]展开后总有一项是 \(\partial L/\partial h_L\) 本身,不随深度衰减。LSTM 的 \(c_t = f_t \odot c_{t-1} + i_t \odot \tilde c_t\) 同理,直接路径上只乘 forget gate。\(f = 0.99\) 时 100 步后还剩 \(0.99^{100} \approx 0.37\),每步乘 0.5 的话只剩 \(0.5^{100} \approx 8\times10^{-31}\)。
ReLU 怎么缓解 vanishing
\[ \mathrm{ReLU}(z) = \max(0, z), \qquad \mathrm{ReLU}'(z) = \begin{cases} 1 & z > 0 \\ 0 & z \le 0 \end{cases} \]Jacobian \(\operatorname{diag}(f')\,W_l\) 里 activation 只管 \(f'\) 这个因子。ReLU 在 \(z > 0\) 时 \(f' = 1\),gradient 经过激活的 neuron 时不被缩小。10 层连乘后,这个因子在 sigmoid 下最多剩 \(0.25^{10} \approx 9.5\times10^{-7}\),在 ReLU 激活的路径上是 1。
ReLU 只去掉了 activation 带来的衰减,\(W\) 的连乘还在。大约一半 neuron 的 \(z \le 0\),gradient 被清零,每层的 gradient norm 约乘 \(\sqrt{n\,\mathrm{Var}(W)/2}\)。He init 取 \(\mathrm{Var}(W) = 2/n\) 让这个倍率正好是 1,所以 ReLU 要和 He init 一起用。下面表里 \(\mathrm{Var}(W) = 1/n\) 的 ReLU 传 20 层只剩约 \(10^{-3}\),就是少了这个 2。
ReLU 自己的问题是 dying ReLU,neuron 对所有输入都有 \(z \le 0\) 时不再更新,详见 activation function。
手算例子
branch 倍率 0.1 时,10 层 plain 网络剩 \(0.1^{10} = 10^{-10}\),residual 是 \((1 + 0.1)^{10} \approx 2.6\)。
20 层、宽 256 的 MLP 刚初始化时,第 1 层 gradient norm ÷ 第 20 层:
| activation | \(\mathrm{Var}(W)\) | 第 1 层 ÷ 第 20 层 |
|---|---|---|
| sigmoid | \(1/n\)(Xavier) | \(\approx 2\times10^{-13}\) |
| ReLU | \(1/n\) | \(\approx 10^{-3}\) |
| ReLU | \(2/n\)(He) | \(\approx 1\) |
| ReLU | \(4/n\) | \(\approx 10^{3}\) |
怎么解决
| 方法 | 治什么 | 为什么有效 |
|---|---|---|
| ReLU / GELU | vanishing | 正区间导数 = 1(上面一节) |
| Xavier / He init | 两者 | 选 \(\mathrm{Var}(W)\) 让各层 activation 和 gradient 的方差不变 |
| BatchNorm / LayerNorm | 两者 | 每层拉回 mean 0、variance 1,尺度不逐层漂移 |
| Residual connection | vanishing | 多一条 identity 通路 |
| Gradient clipping | exploding | \(\|g\| > c\) 时缩放到 norm \(c\),方向不变。例:\((3, 4)\),\(c = 1\) → \((0.6, 0.8)\) |
| LSTM / GRU | RNN | cell state 加法更新,不再反复乘同一个 \(W\) |
必答点
- 原因:各层 Jacobian 连乘,norm < 1 指数衰减,> 1 指数爆炸
- sigmoid \(\sigma' \le 1/4\) 加剧 vanishing;RNN 连乘同一个 \(W\),最严重
- ReLU:正区间 \(f' = 1\),去掉了 activation 带来的衰减;要配 He init;缺点是 dying ReLU
- 症状:前几层的 gradient norm 小几个数量级、loss 停滞;或 norm 飙升、loss 变 NaN
- 解决:ReLU、Xavier / He、BN / LN、residual、clipping、LSTM / GRU
追问
为什么 He init 是 \(2/n\),Xavier 是 \(1/n\)?
输出 variance = \(n_{\text{in}}\,\mathrm{Var}(W)\,\mathbb{E}[x^2]\),要它等于输入 variance 就取 \(\mathrm{Var}(W) = 1/n_{\text{in}}\),兼顾 backward 的 Xavier 取 \(2/(n_{\text{in}} + n_{\text{out}})\)。ReLU 把一半清零,\(\mathbb{E}[x^2]\) 少一半,所以 He 乘回 2,取 \(2/n_{\text{in}}\)。
ResNet 解决的就是 vanishing gradient 吗?
ResNet 原文说 vanishing / exploding 已被 normalized initialization 和 BatchNorm 基本解决,它针对的是 degradation,plain 网络加深后连 training error 都变高。identity shortcut 既让 gradient 直接回传(Identity Mappings 论文),也让深网络更好优化。
Transformer 里为什么 Pre-LN 比 Post-LN 稳?
Pre-LN 把 LayerNorm 放进 residual branch 里,初始化时 gradient 更平稳,可以去掉 warmup,见 Transformer architecture。
来源Murphy, PML1 §13.4.2–13.4.5(pp.447–453)· Goodfellow et al., DL §8.2.4–8.2.5(pp.285–287)· 同书 §10.7–10.11(pp.396–410)· He init §2.2 · ResNet §1 · Identity Mappings · Xiong et al. 2020