halo 的技术博客

返回

一条国债收益率曲线,上有 3 个月、下有 30 年,中间十几个关键期限,每个期限一个即期利率。如果我们想「理解」这条曲线,难道要给 11 个期限各建一个模型?不需要。经验告诉我们,整条曲线 90% 以上的变动,只由三个动作驱动:整体上下(水平)、长短端利差变化(斜率)、中段相对两端鼓起或塌陷(曲率)。 Nelson-Siegel(1987)用一个极简的函数,把这三个动作压缩成三个因子。

结论先放这里:NS 模型用 4 个参数(3 个因子 + 1 个衰减参数 λ)就能高保真拟合整条收益率曲线,且三个因子有明确的经济含义——β0 是长端水平、β1 是短长端利差、β2 是中段曲率。它们是利率建模、曲线估值、风险分解的「最小可行因子」。

Nelson-Siegel 收益率曲线拟合与三因子分解

一、为什么需要「节俭」的曲线模型#

收益率曲线上的点高度共线:1 年和 2 年的利率几乎永远同涨同跌;10 年和 15 年也高度同步。如果你对每个期限独立建模,会得到 11 个高度相关的序列,参数爆炸、过拟合、还无法解释。

更好的思路是因子降维:把曲线看成「少数几个形状(shape)的线性组合」。NS 提出的三形状是:

  • 水平(level):整条曲线一起平移——所有期限同涨同跌;
  • 斜率(slope):短端和长端反向——曲线变陡或变平;
  • 曲率(curvature):中段相对两端凸起或塌陷——典型的「驼背」形态。

这三个形状几乎能解释收益率曲线协方差矩阵的绝大部分。

二、Nelson-Siegel 的函数形式#

NS 把期限 τ 处的即期利率写成:

y(τ)=β0+β11eτ/λτ/λ+β2(1eτ/λτ/λeτ/λ)y(\tau) = \beta_0 + \beta_1 \frac{1 - e^{-\tau/\lambda}}{\tau/\lambda} + \beta_2 \left( \frac{1 - e^{-\tau/\lambda}}{\tau/\lambda} - e^{-\tau/\lambda} \right)

三个载荷(loading)函数分别是:

  • 水平载荷:常数 1(对所有期限一样);
  • 斜率载荷:c1(τ)=(1eτ/λ)/(τ/λ)c_1(\tau) = (1 - e^{-\tau/\lambda}) / (\tau/\lambda),在短端为 1、随期限单调衰减到 0;
  • 曲率载荷:c2(τ)=c1(τ)eτ/λc_2(\tau) = c_1(\tau) - e^{-\tau/\lambda},在短端为 0、中段达到峰值、长端回到 0——这就是「蝴蝶型」。

λ 是唯一的「形状」参数,它决定斜率和曲率在哪个期限区间作用最明显。λ 越小,曲率峰越往短端挤;λ 越大,越往长端延。

三、Python:用 scipy 拟合一条曲线#

我们用 scipy.optimize.least_squares 对一组(含噪声的)观测点做非线性最小二乘拟合:

跑出来大致是 β0≈4.0(长端水平约 4%)、β1≈-1.5(斜率负、曲线向上倾斜)、β2≈1.0(中段略鼓)。四个参数,就把 11 个点的曲线拟合到误差 < 5bps。图 1 同时画出了观测点、拟合曲线和三大成分分解——你能直观看到「水平」是那条水平线、「斜率」是短高长低的倾斜、「曲率」是 mid 段的鼓包。

四、三因子的时序演化#

把 NS 模型对每一天的曲线都拟合一遍,把每天的 (β0, β1, β2) 连起来,就得到三条因子时序(图 2):

Nelson-Siegel 三因子时序

它们的经济含义非常干净:

  • β0(水平):跟随长期经济增长与通胀预期,最平滑、最持久;
  • β1(斜率):跟随货币政策周期——加息周期斜率压平甚至倒挂,宽松周期陡峭化;
  • β2(曲率):最「跳」,反映市场对中段(比如 2–5 年)的供需错配或预期突变。

五、载荷曲线:λ 决定形状的作用区间#

图 3 展示了不同 λ 下斜率载荷和曲率载荷的形状:

Nelson-Siegel 载荷曲线

  • λ 小(如 0.3):曲率峰值挤在 1 年以内,模型主要刻画短端弯曲;
  • λ 大(如 1.0):曲率峰延伸到 3–5 年,模型更关注中段。

实务中 λ 常固定为 0.5 或 1.0(对应半衰期约 0.5 / 1 年),也可以把它作为第 4 个待估参数让数据自己选形状——代价是优化非凸、可能对初值敏感,需要多组初值网格搜索。

六、NS 与主成分(PCA):为什么选 NS 而不是 PCA#

有人会问:既然要降维,直接用 PCA 对收益率曲线做主成分分解不行吗?行,而且 PCA 的「前三大主成分」在形状上几乎就是水平、斜率、曲率——和 NS 三因子高度对应。但 NS 有两个 PCA 给不了的优势:

  1. 可解释性:NS 的 β 有直接的利率含义,能和宏观经济叙事对接;PCA 的主成分是「统计构造」,解释起来要绕一圈。
  2. 外推与插值:NS 是闭式函数,给任意一个 τ 都能算利率;PCA 只在观测期限上有载荷,中间期限要靠插值。

代价是 NS 拟合是非线性的(含 λ),PCA 是线性的、有解析解。实务里常见做法是:用 PCA 定 λ(让 NS 曲率峰对准 PCA 能量最大的期限),再用 NS 做可解释建模

from sklearn.decomposition import PCA
pca = PCA(n_components=3)
scores = pca.fit_transform(y_curve_panel)        # 每行一条曲线
print("前3主成分解释度:", pca.explained_variance_ratio_.cumsum())
# 通常 cumsum 第3项 > 0.98,说明三因子足够刻画曲线
python

七、NS 模型的四个局限#

NS 很美,但别神化它:

  1. 无套利(no-arbitrage)缺失:NS 直接拟合即期利率,不保证由它推导的远期利率曲线无套利。想做定价,得上其扩展 Nelson-Siegel-Svensson(加第 4 个曲率因子)动态无套利模型(如 Hull-White / affine term structure)
  2. λ 固定的代价:固定 λ 等于先验「曲率只在中段」;若某段曲线在短端鼓包(如 2023 年美债短端倒挂加剧),固定 λ 的 NS 拟合会系统性偏差。
  3. 外推危险:NS 在观测期限范围内拟合好,但拿去外推 50 年、100 年,c1、c2 都趋近于 0,曲线会平铺在 β0——这对养老金长负债贴现是隐患。
  4. 因子正交性假象:β0/β1/β2 在载荷层面「形状不同」,但估计时仍可能高度相关(尤其 β1 与 β2),做风险分解时要小心共线。

结论#

Nelson-Siegel 是利率曲线建模的「最小可行起点」:4 个参数、3 个可解释因子、闭式载荷、拟合快、含义清。它是曲线估值、债券相对价值(见上一篇信用利差因子)、利率风险分解的通用语言。等你需要的不再是「描述曲线」而是「给衍生品无套利定价」时,再从 NS 升级到 Svensson 或无套利动态模型——但无论如何,NS 都是你理解期限结构的那把第一把尺子。

如果你要把它接上真实数据,下一步是用 中国国债收益率曲线(中债登每日发布的关键期限点)循环拟合、把每日 (β0, β1, β2) 存成因子面板,再对因子自身做均值回复或预测——那时你得到的,是一个可交易、可风控的利率曲线因子库。

所有图表均由文中 Python 代码真实计算生成(模拟数据),仅用于方法演示,不构成投资建议。

利率期限结构 Nelson-Siegel 模型:用少数因子刻画整条收益率曲线
https://blog.halo26812.eu.org/blog/nelson-siegel-term-structure
Author halo
Published at 2026年7月11日
版权声明 CC BY-NC-SA 4.0
Comment seems to stuck. Try to refresh?✨