第三节:插值方法入门——线性插值与三次样条插值在曲面构建中的应用
各位同学,咱们今天聊聊插值。说实话,我刚入行做期权做市那会儿,最头疼的就是曲面构建。交易所给的报价就那么几个点,可做市需要全市场、全期限的波动率数据。怎么办?插值。
说白了,插值就是「用已知点去猜未知点」。你手上有几个期限的隐含波动率,想得到任意期限的值,就得靠插值。今天我只讲两种最常用的:线性插值和三次样条插值。
一、线性插值——简单粗暴,但够用
线性插值,名字听着唬人,其实就是两点之间画直线。假设你有两个已知点 (x₁, y₁) 和 (x₂, y₂),想求中间某个 x 对应的 y,公式就一个:
y = y₁ + (x - x₁) * (y₂ - y₁) / (x₂ - x₁)
嗯,就这么简单。我当年第一次写代码做曲面时,第一版用的就是线性插值。为什么?因为快,而且不容易出错。
实战场景:你手上有1个月和3个月的平值隐含波动率,分别是18.5%和19.2%。现在客户问2个月的波动率是多少?线性插值一算:
y = 18.5 + (2-1) * (19.2-18.5) / (3-1) = 18.5 + 0.35 = 18.85%
简单吧?
但线性插值有个硬伤——一阶导数不连续。什么意思?就是在已知点处,斜率会突变。你想想看,波动率曲面应该是光滑的,突然来个折角,这合理吗?不合理。尤其在做希腊值计算时,这种不连续会导致Delta、Gamma出现跳跃,做市报价就会不稳定。
我曾经踩过的坑:有一次用线性插值做波动率曲面,回测时发现某个期限附近的期权Delta突然跳变。排查了半天,发现就是插值点处导数不连续导致的。从那以后,我对线性插值的使用就谨慎多了。
二、三次样条插值——光滑才是王道
三次样条插值,说白了就是每两个已知点之间用一条三次曲线连接,并且保证在连接点处一阶导数和二阶导数都连续。这样整个曲线就是光滑的,没有折角。
数学上,三次样条函数 S(x) 满足:
- 在每个区间 [xᵢ, xᵢ₊₁] 上,S(x) 是三次多项式
- S(xᵢ) = yᵢ,即通过所有已知点
- S'(x) 和 S''(x) 在整个区间上连续
为什么选三次?因为三次多项式有4个系数,正好可以满足4个约束条件:两个端点值、一阶导数连续、二阶导数连续。再高次就过拟合了,再低次就不够光滑了。
我个人习惯:在做市系统中,我通常对期限维度用三次样条,对执行价维度用线性插值。为什么?因为期限结构通常比较平滑,适合样条;而执行价维度上,尤其是深度实值和深度虚值区域,波动率变化剧烈,线性插值反而更稳健。
三、代码实现——别光说不练
咱们直接上代码。Python里实现三次样条插值,最方便的就是 scipy.interpolate 模块。
import numpy as np
from scipy.interpolate import CubicSpline
import matplotlib.pyplot as plt
# 已知数据点:期限(月)和对应的隐含波动率
tenors = np.array([1, 3, 6, 12])
vols = np.array([0.185, 0.192, 0.198, 0.205])
# 构建三次样条插值函数
cs = CubicSpline(tenors, vols, bc_type='natural')
# 生成密集的期限点用于绘图
tenors_dense = np.linspace(1, 12, 100)
vols_dense = cs(tenors_dense)
# 线性插值作为对比
from scipy.interpolate import interp1d
linear = interp1d(tenors, vols, kind='linear')
vols_linear = linear(tenors_dense)
# 绘图对比
plt.figure(figsize=(10, 6))
plt.plot(tenors, vols, 'o', label='已知点', markersize=8)
plt.plot(tenors_dense, vols_dense, '-', label='三次样条插值', linewidth=2)
plt.plot(tenors_dense, vols_linear, '--', label='线性插值', linewidth=2)
plt.xlabel('期限(月)')
plt.ylabel('隐含波动率')
plt.legend()
plt.title('线性插值 vs 三次样条插值')
plt.grid(True)
plt.show()
你看,代码就这么几行。但实际做市系统中,我建议你注意两点:
- 边界条件:bc_type='natural' 表示自然样条,两端二阶导数为0。如果你有先验知识,比如长期波动率趋于某个值,可以用 clamped 边界条件。
- 外推问题:样条插值在外推时非常不稳定。我见过有人用样条外推出负波动率的,那真是灾难。所以,永远不要用样条做外推。
四、曲面构建的核心逻辑
好了,咱们把插值方法放到曲面构建的大框架里看看。下面这张图是我自己画的,帮你理清思路:
你看,整个流程其实不复杂。输入是交易所给的有限报价点,先对期限维度做三次样条插值,再对执行价维度做线性插值,最后生成一个完整的网格。这个网格就是你的波动率曲面。
五、实战中的选择建议
说了这么多,到底什么时候用线性,什么时候用样条?我根据自己的经验给你列个表:
| 场景 | 推荐方法 | 原因 |
|---|---|---|
| 期限维度,数据点稀疏(<5个) | 三次样条 | 保证光滑性,避免折角 |
| 执行价维度,近月合约 | 线性插值 | 近月波动率变化剧烈,样条易过拟合 |
| 执行价维度,远月合约 | 三次样条 | 远月波动率平滑,样条效果更好 |
| 实时报价,要求低延迟 | 线性插值 | 计算量小,速度快 |
| 回测研究,追求精度 | 三次样条 | 精度更高,但注意边界条件 |
我的经验之谈:做市系统里,我通常把插值方法做成可配置的。不同品种、不同市场环境下,切换不同的插值策略。比如在股指期权上,我偏好样条;在个股期权上,因为流动性差、报价稀疏,我反而用线性更稳。
六、避坑指南
最后,分享几个我踩过的坑,你遇到了能少走弯路:
- 不要用样条外推:样条在数据范围之外的表现极其不稳定,可能给出荒谬的值。我见过有人用样条外推出200%的波动率,那还做个屁的市。
- 注意数据点的分布:如果已知点分布不均匀,样条插值在稀疏区域会振荡。这时候我建议先对数据做预处理,或者改用分段线性插值。
- 检查插值结果的单调性:波动率曲面应该是单调的(至少局部单调)。如果插值结果出现非单调,那一定是数据或方法有问题。
- 回测时一定要做稳定性测试:我曾经用样条插值做回测,结果发现某个参数微调后,曲面形状大变。这就是过拟合的表现。
好了,插值方法就讲到这里。记住,工具是死的,人是活的。理解每种方法的优缺点,根据实际情况灵活选择,这才是做市交易员的真本事。
公众号:蓝海资料掘金营,微信deep3321