特征工程基础:特征构建、变换与筛选
大家好,我是老K。今天咱们聊聊特征工程——这个在量化投资里被反复提及,却又容易被忽视的环节。说实话,我见过太多人把精力全花在模型调参上,结果特征质量不行,模型再花哨也是白搭。特征工程做得好,Alpha挖掘就成功了一半。
核心观点:特征工程不是简单的数据搬运,而是对市场信息的深度加工。好的特征能放大信号,差的特征只会引入噪声。
3.1 特征构建思路
特征构建,说白了就是从原始数据里提炼出有价值的信息。我个人习惯把特征分成三大类:价格类、成交量类、波动率类。这三类特征基本覆盖了市场行为的方方面面。
3.1.1 价格类特征
价格是最直观的数据。但直接拿收盘价做特征?那太粗糙了。我在项目中常用的价格特征包括:
- 收益率:简单差分,但要注意对数收益率和简单收益率的区别
- 价格位置:当前价格在近期高低点中的位置,比如(close - low) / (high - low)
- 价格形态:开盘收盘关系、上下影线长度等
我的经验:价格位置类特征在震荡市中表现不错,但在趋势行情里容易失效。我一般会结合市场状态动态调整权重。
3.1.2 成交量类特征
成交量是价格的佐证。量价配合才是好信号。我曾经踩过一个坑:只看价格突破,没看成交量,结果频繁假突破。后来加了成交量特征,效果立竿见影。
常用的成交量特征:
- 成交量变化率(volume / 过去N日均量)
- 量价相关性(比如价格涨时量是否放大)
- 成交量分布(大单占比、成交集中度)
3.1.3 波动率类特征
波动率是市场的"体温"。高波动意味着不确定性大,低波动则可能酝酿变盘。我个人习惯用以下方式刻画波动率:
- 历史波动率:过去N日收益率的标准差
- 振幅波动率:(high - low) / close,日内波动幅度
- 已实现波动率:高频数据计算的波动率,更精确
注意:波动率特征有聚集效应——高波动之后往往还是高波动。这个特性在做风险控制时特别重要。
3.2 特征变换
原始特征往往不满足模型要求。比如收益率分布偏态严重,或者存在异方差性。这时候就需要做特征变换。我常用的变换手段有三种:
3.2.1 对数变换
对数变换能把乘法关系变成加法关系,还能压缩数据范围。比如价格序列,直接做差分得到的是绝对变化,而对数差分得到的是相对变化——这在金融里更有意义。
import numpy as np
import pandas as pd
# 对数收益率
prices = pd.Series([100, 102, 101, 105, 103])
log_returns = np.log(prices / prices.shift(1))
print(log_returns)
# 输出:NaN, 0.0198, -0.0099, 0.0392, -0.0194
小技巧:对数收益率在时间上可加,但截面不可加。简单收益率则相反。选哪个?看你的应用场景。
3.2.2 差分变换
差分是为了让非平稳序列变平稳。金融数据大多是非平稳的,直接建模会出问题。一阶差分通常能解决大部分问题。
# 一阶差分
diff_prices = prices.diff()
print(diff_prices)
# 输出:NaN, 2.0, -1.0, 4.0, -2.0
嗯,这里要注意:差分会损失一个观测值。如果你的数据量不大,可以考虑用其他方法,比如HP滤波或者移动平均去趋势。
3.2.3 滚动窗口统计量
滚动窗口是特征工程里最常用的操作。它能捕捉局部特征,比如过去20天的平均收益率、最大回撤等。
# 滚动窗口均值
rolling_mean = prices.rolling(window=3).mean()
print(rolling_mean)
# 输出:NaN, NaN, 101.0, 102.67, 103.0
滚动窗口的窗口大小怎么选?我一般会试多个尺度:5天、10天、20天、60天。不同尺度捕捉不同周期的信号。你想想看,短线交易者和长线投资者关注的信息能一样吗?
3.3 特征筛选
特征造了一大堆,但很多是冗余的。不筛选的话,模型容易过拟合,训练速度也慢。我常用的筛选方法有两个:
3.3.1 相关性分析
特征之间相关性太高,说明信息重复。我一般设定阈值0.7——超过这个值的特征,只保留一个。
| 特征对 | 相关系数 | 处理方式 |
|---|---|---|
| 收益率_5日 vs 收益率_10日 | 0.85 | 保留一个 |
| 成交量 vs 成交额 | 0.92 | 保留成交额 |
| 波动率_5日 vs 波动率_20日 | 0.45 | 都保留 |
避坑指南:我曾经把所有低相关特征都留下,结果模型在测试集上表现很好,实盘却一塌糊涂。后来发现,低相关不代表低噪声——有些特征纯粹是随机波动。
3.3.2 IC值分析
IC值(Information Coefficient)衡量特征与未来收益的相关性。IC值越高,说明特征的预测能力越强。我一般会计算Rank IC,因为它对异常值不敏感。
# 计算Rank IC
from scipy.stats import spearmanr
feature = pd.Series([0.1, 0.2, -0.1, 0.05, -0.2])
future_return = pd.Series([0.05, 0.15, -0.05, 0.02, -0.1])
rank_ic, p_value = spearmanr(feature, future_return)
print(f"Rank IC: {rank_ic:.3f}, p-value: {p_value:.3f}")
# 输出:Rank IC: 0.900, p-value: 0.037
IC值多少算好?我个人经验:
- IC绝对值 > 0.05:有预测能力
- IC绝对值 > 0.1:不错的特征
- IC绝对值 > 0.2:非常强的特征(但很少见)
我的习惯:IC值要结合稳定性看。一个特征IC值高但波动大,不如IC值中等但稳定的特征。我一般会看IC的IR(信息比率),即IC均值除以IC标准差。
3.4 本章知识体系
下面这张图总结了特征工程的完整流程。从原始数据出发,经过构建、变换、筛选三步,最终得到高质量的特征集。
这张图展示了特征工程的三个核心步骤:构建、变换、筛选。每一步都有其独特的作用,缺一不可。我个人习惯在构建阶段多造一些特征,然后在筛选阶段严格把关——宁可漏掉一个弱信号,也不要引入一个强噪声。
本章小结:特征工程是量化投资的基石。好的特征能让简单的模型跑出好效果,差的特征再牛的模型也救不了。记住三个关键词:构建要全面、变换要合理、筛选要严格。