3. 时间序列数据特性:金融时间序列的平稳性、自相关性、非独立同分布特性对标签对齐的影响
金融时间序列与普通机器学习数据集存在本质区别。普通监督学习假设样本独立同分布(i.i.d.),而金融数据天然具有时间依赖性、非平稳性和序列自相关。这些特性直接影响标签对齐策略:如果忽略时间结构,回测将产生严重的未来信息泄露和过拟合。
3.1 平稳性:统计性质随时间漂移
平稳时间序列的均值、方差和自协方差在时间平移下保持不变。金融收益率序列通常呈现弱平稳(均值恒定、方差有限),但波动率、价差等特征常表现出非平稳性。
| 平稳类型 | 定义 | 金融实例 | 对齐影响 |
|---|---|---|---|
| 严格平稳 | 联合分布对时间平移不变 | 极少见,仅理想模型 | 标签分布稳定,可直接对齐 |
| 弱平稳 | 一阶矩、二阶矩恒定 | 日收益率(近似) | 需滚动窗口重估统计量 |
| 趋势非平稳 | 均值随时间变化 | 股价、累计收益 | 必须差分或去趋势后对齐 |
| 异方差非平稳 | 方差随时间变化 | 波动率聚集(GARCH) | 标签阈值需动态调整 |
关键实践:在标签对齐前,对特征和标签序列执行滚动ADF检验。若p值>0.05,则序列非平稳,需先进行一阶差分或使用对数收益率,再构造标签。
3.2 自相关性:过去影响未来
金融时间序列的当前值往往与历史值相关。自相关函数(ACF)和偏自相关函数(PACF)量化这种依赖强度。自相关性对标签对齐的影响体现在三个方面:
- 标签泄漏:若标签使用未来信息(如未来N期收益率),而特征包含滞后变量,自相关会导致特征与标签隐含共享同一段噪声。
- 样本重叠:滚动标签窗口(如未来5日收益)使相邻样本的标签高度相关,降低有效样本量。
- 过拟合风险:模型可能学到自相关模式而非真实因果关系,在样本外失效。
3.3 非独立同分布特性:时间依赖结构
金融数据违反i.i.d.假设的具体表现包括:
- 时间依赖性:t时刻的观测与t-1时刻相关,不能随机打乱样本。
- 波动率聚集:大波动后常跟随大波动,方差非恒定。
- 尾部依赖:极端收益在时间上聚集出现。
- 结构性突变:政策、危机导致数据生成过程改变。
对齐规则:在构造标签时,必须保留时间索引。训练集、验证集、测试集按时间顺序划分,禁止随机洗牌。标签窗口(如未来N期收益)必须完全位于当前时间点之后,且不能与特征窗口重叠。
3.4 标签对齐的三大时间约束
| 约束类型 | 描述 | 违反后果 | 解决方案 |
|---|---|---|---|
| 因果约束 | 标签只能使用t时刻之后的信息 | 未来信息泄露,回测虚高 | 严格时间戳对齐,禁止前视偏差 |
| 平稳性约束 | 标签分布应在时间上相对稳定 | 模型在样本外失效 | 滚动窗口标准化,差分处理 |
| 独立性约束 | 相邻标签不应高度相关 | 有效样本量虚增,统计检验失真 | 跳跃采样、去相关标签、Purged CV |
3.5 实践检查清单
- 平稳性检查:对标签序列执行ADF检验和KPSS检验。
- 自相关检查:绘制ACF/PACF图,计算Ljung-Box Q统计量。
- 时间戳验证:确保特征窗口结束时间 < 标签窗口开始时间。
- 重叠度计算:统计相邻标签窗口的重叠比例,若>50%则需调整。
- 分布稳定性:将时间序列分段,比较各段标签的均值和标准差。
常见陷阱:使用未来N期收益率作为标签时,若特征包含过去N期收益率,则特征与标签共享N-1期重叠数据,导致严重的自相关泄漏。务必使用非重叠窗口或去相关残差作为标签。
3.6 时间序列对齐的SVG流程
3.7 代码示例:时间序列对齐检查
import pandas as pd
import numpy as np
from statsmodels.tsa.stattools import adfuller
from statsmodels.stats.diagnostic import acorr_ljungbox
def check_time_series_alignment(df, feature_cols, label_col, timestamp_col):
"""
检查时间序列标签对齐的三大约束
Parameters:
-----------
df : DataFrame, 包含特征、标签、时间戳
feature_cols : list, 特征列名
label_col : str, 标签列名
timestamp_col : str, 时间戳列名
Returns:
--------
dict, 检查结果
"""
results = {}
# 1. 因果约束检查
df_sorted = df.sort_values(timestamp_col)
# 假设特征使用过去数据,标签使用未来数据
# 检查特征中是否包含未来信息(示例:检查标签时间是否晚于特征时间)
results['causality_check'] = '通过' # 实际需根据窗口定义实现
# 2. 平稳性检查(ADF检验)
label_series = df_sorted[label_col].dropna()
adf_result = adfuller(label_series, autolag='AIC')
results['adf_statistic'] = adf_result[0]
results['adf_pvalue'] = adf_result[1]
results['is_stationary'] = adf_result[1] < 0.05
# 3. 自相关检查(Ljung-Box)
lb_result = acorr_ljungbox(label_series, lags=[10], return_df=True)
results['lb_statistic'] = lb_result['lb_stat'].values[0]
results['lb_pvalue'] = lb_result['lb_pvalue'].values[0]
results['has_significant_autocorr'] = lb_result['lb_pvalue'].values[0] < 0.05
# 4. 标签重叠度计算(假设标签窗口长度为N)
# 示例:计算相邻标签的相关系数
label_diff = label_series.diff().dropna()
overlap_corr = label_series.iloc[1:].corr(label_series.iloc[:-1])
results['adjacent_label_corr'] = overlap_corr
results['overlap_warning'] = overlap_corr > 0.5
return results
# 使用示例
check_results = check_time_series_alignment(
df=price_data,
feature_cols=['returns_lag1', 'returns_lag2', 'volume_lag1'],
label_col='future_5d_return',
timestamp_col='date'
)
print(f"平稳性p值: {check_results['adf_pvalue']:.4f}")
print(f"自相关p值: {check_results['lb_pvalue']:.4f}")
print(f"相邻标签相关性: {check_results['adjacent_label_corr']:.3f}")
核心结论:金融时间序列的平稳性、自相关性和非独立同分布特性是标签对齐必须处理的三座大山。忽略其中任何一个,都会导致回测结果不可靠。正确的做法是:先诊断时间序列特性,再设计对齐策略,最后用时间感知的交叉验证评估。