第八章:机器学习辅助:使用PCA降维曲面数据、聚类算法识别形态、LSTM预测曲面变化
各位,欢迎来到第八章。
前面几章我们聊了怎么手工识别曲面形态,怎么用参数化模型去拟合。但说实话,手工看曲面,一天看个几十次还行,要是做高频或者批量扫描几百个品种,眼睛就花了。我早年做CTA策略回测时,就吃过这个亏——人工标注了三千个曲面样本,结果脖子疼了一周,还漏掉了几次关键的结构转换信号。
所以这一章,我们聊聊怎么让机器帮我们干这活。核心思路就三步:降维、聚类、预测。说白了,就是把高维的曲面数据压缩成几个关键特征,然后让算法自己学会“这是什么形态”,最后用时序模型猜一猜“下一步会变成什么样”。
核心逻辑框架:原始曲面(10×10网格)→ PCA降维(3-5个主成分)→ K-Means聚类(识别牛陡、熊平、蝶式等形态)→ LSTM时序预测(预测未来曲面主成分)→ 生成交易信号。
8.1 为什么要降维?—— 曲面数据的“维度诅咒”
一个标准的波动率曲面,假设期限有10档,行权价有10档,那就是100个数据点。你想想看,100维的空间里做聚类,距离度量基本失效——所有点之间的距离都差不多,聚类结果毫无意义。这就是所谓的“维度诅咒”。
我2018年刚尝试用机器学习做曲面分类时,直接拿100维数据跑K-Means,结果分出来的类别完全随机,跟扔骰子差不多。后来才意识到,必须先降维。
我的经验:PCA降维后保留的主成分数量,我一般取能解释总方差95%以上的前几个。对于外汇期权曲面,通常是3-5个;对于股指期权,有时需要6-7个。你可以画个“碎石图”看看拐点在哪。
8.2 PCA降维实战:从100维到5维
PCA的原理不复杂,就是找数据方差最大的方向。具体到曲面数据,第一主成分通常对应“整体波动率水平”,第二主成分对应“期限结构的斜率”,第三主成分对应“微笑曲率”。
import numpy as np
from sklearn.decomposition import PCA
from sklearn.preprocessing import StandardScaler
# 假设曲面数据 shape = (n_samples, 100)
# 每一行是一个展平的曲面(10期限 × 10行权价)
X = np.random.randn(5000, 100) # 示例数据
# 标准化:PCA对尺度敏感
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)
# 执行PCA,保留95%方差
pca = PCA(n_components=0.95)
X_pca = pca.fit_transform(X_scaled)
print(f"原始维度: {X.shape[1]}")
print(f"降维后维度: {X_pca.shape[1]}")
print(f"各主成分解释方差比: {pca.explained_variance_ratio_}")
跑完这段代码,你会发现前3个主成分通常能解释70%-80%的方差,前5个能到95%以上。我习惯把前三个主成分分别命名为:水平因子、斜率因子、曲率因子。这样解释起来很直观。
注意:PCA假设数据是线性的。如果曲面形态存在明显的非线性结构(比如极端行权价处的“翘尾”),你可能需要尝试核PCA或t-SNE。不过对于大多数常规市场,线性PCA已经够用。
8.3 聚类算法识别形态:让机器自己学会分类
降维之后,我们就可以在低维空间里做聚类了。我推荐用K-Means,简单、快、可解释性强。但有个问题:K值怎么选?
我个人习惯用“肘部法则”加“业务理解”双重验证。比如你先跑K=2到K=10,看每个K对应的SSE(簇内平方和),找到拐点。然后看看每个簇的中心点对应的曲面长什么样——如果K=4时,四个中心分别对应“牛陡”、“熊平”、“蝶式正”、“蝶式负”,那就很完美。
from sklearn.cluster import KMeans
import matplotlib.pyplot as plt
# 用肘部法则选K
sse = []
for k in range(2, 11):
kmeans = KMeans(n_clusters=k, random_state=42, n_init=10)
kmeans.fit(X_pca)
sse.append(kmeans.inertia_)
# 画图看拐点
plt.plot(range(2, 11), sse, marker='o')
plt.xlabel('K')
plt.ylabel('SSE')
plt.title('肘部法则确定最佳K值')
plt.show()
# 假设拐点在K=5
kmeans = KMeans(n_clusters=5, random_state=42, n_init=10)
labels = kmeans.fit_predict(X_pca)
# 每个簇的中心点(在主成分空间)
centers_pca = kmeans.cluster_centers_
# 反变换回原始曲面空间,看看每个形态长什么样
centers_original = pca.inverse_transform(centers_pca)
我曾经用这个方法在欧元兑美元期权上跑过一次。聚类结果很有意思:K=5时,五个簇分别对应“平稳市”、“陡峭牛”、“平坦熊”、“左偏微笑”、“右偏微笑”。而且我发现,当市场从“平稳市”切换到“左偏微笑”时,往往预示着尾部风险在积聚——这个信号后来帮我躲过了一次闪崩。
避坑指南:聚类结果不是一成不变的。我建议每周重新训练一次模型,或者用滚动窗口的方式更新聚类中心。市场结构会变,去年的“牛陡”和今年的“牛陡”可能不是一回事。
8.4 LSTM预测曲面变化:从分类到预测
聚类只能告诉我们“现在是什么形态”,但交易需要知道“接下来会变成什么”。这时候就需要时序模型了。
LSTM(长短期记忆网络)特别适合处理这种序列数据。我们的输入是过去N个时间步的PCA主成分,输出是未来M个时间步的主成分。然后我们可以把预测出的主成分反变换回曲面,看看未来曲面长什么样。
import tensorflow as tf
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import LSTM, Dense, Dropout
# 构造序列数据:用过去20个时间步预测未来5个时间步
def create_sequences(data, seq_length=20, pred_length=5):
X, y = [], []
for i in range(len(data) - seq_length - pred_length + 1):
X.append(data[i:i+seq_length])
y.append(data[i+seq_length:i+seq_length+pred_length])
return np.array(X), np.array(y)
# 假设X_pca是降维后的数据,shape=(n_samples, n_components)
X_seq, y_seq = create_sequences(X_pca, seq_length=20, pred_length=5)
# 划分训练集和测试集
split = int(0.8 * len(X_seq))
X_train, X_test = X_seq[:split], X_seq[split:]
y_train, y_test = y_seq[:split], y_seq[split:]
# 构建LSTM模型
model = Sequential([
LSTM(64, activation='tanh', return_sequences=True, input_shape=(20, X_pca.shape[1])),
Dropout(0.2),
LSTM(32, activation='tanh', return_sequences=False),
Dropout(0.2),
Dense(5 * X_pca.shape[1]), # 预测5个时间步 × n_components
tf.keras.layers.Reshape((5, X_pca.shape[1]))
])
model.compile(optimizer='adam', loss='mse')
model.summary()
# 训练
history = model.fit(X_train, y_train, epochs=50, batch_size=32,
validation_data=(X_test, y_test), verbose=1)
训练完成后,我们就可以用最新的20个时间步数据,预测未来5个时间步的曲面主成分。然后反变换回原始曲面空间,看看未来曲面长什么样。
我的小技巧:LSTM预测的曲面不要直接用于交易。我通常会把预测结果和当前曲面做个对比,计算“预测变化量”。如果预测显示未来曲面会从“牛陡”变成“熊平”,而且变化幅度超过历史90分位数,我才会考虑入场。说白了,预测是辅助,不是圣杯。
8.5 完整流程:从数据到信号
把上面三步串起来,就是一个完整的机器学习辅助交易系统:
- 数据准备:获取实时曲面数据,展平成100维向量,标准化。
- PCA降维:用预训练的PCA模型,将100维降到5维主成分。
- 形态识别:用预训练的K-Means模型,给当前主成分打上形态标签。
- 趋势预测:用LSTM模型,基于过去20个时间步的主成分,预测未来5步。
- 信号生成:结合当前形态标签和预测变化,生成交易信号。
| 当前形态 | 预测变化 | 交易信号 |
|---|---|---|
| 牛陡 | → 熊平 | 做空短期波动率,做多长期波动率 |
| 蝶式正 | → 蝶式负 | 卖出蝶式价差,买入反向蝶式 |
| 平稳市 | → 左偏微笑 | 买入虚值看跌期权对冲尾部风险 |
重要提醒:机器学习模型在市场结构发生剧烈变化时(比如2020年3月、2008年金融危机)会失效。因为这些极端行情在训练数据中很少出现。我建议设置一个“模型置信度”阈值——当预测结果和历史分布偏差超过3个标准差时,自动切换到规则交易模式。
好了,这一章的内容就到这里。PCA降维、K-Means聚类、LSTM预测,这三板斧用好了,能帮你从海量曲面数据中快速提取交易信号。但记住,机器是辅助,最终决策还是要靠你对市场的理解。