走查验证(Walk-Forward):把样本外拼接成诚实净值
我的掌握程度:
先掌握这个答案
Walk-Forward协议:滚动推进——用[2016-2018]训练→预测2019;再[2017-2019]训练→预测2020;…直到尽头;把各段「真样本外预测」拼成完整净值曲线。三个纪律:①每段的参数/模型只能用该段训练数据确定(连因子筛选、超参数都要在段内完成);②段与段之间不留任何「看过未来」的缝隙(含标签重叠的清洗,q-710的Embargo预告);③拼接净值的换手跨段处要计成本(参数变化引发的调仓)。解读:拼接曲线≈策略「如果当年真实运行」的成绩单——它仍有幸存者偏差(策略本身可能筛选过),但已是回测能给的最高诚实度。
先读结论,再核对下方使用边界;数字例题为教学情景,涉及实际行情与规则时请核对原始来源。
从理解到使用
按标签区间检查泄漏
以实际预测目标设计时间切分,检查每条标签观察区间是否跨过验证边界。标准化、填充、特征选择和调参仅在训练内拟合;只按日期切开仍可能因标签重叠产生泄漏。
核对来源:scikit-learn:时间序列交叉验证 ↗本阶段实战方法 · 回测先过时序、成交与成本三道关
把信号变成策略收益时,每笔收益必须能追溯到当时能下出的订单。
- 画出时间线:数据可得→算信号→下单→成交→持仓收益;收盘信号不能倒用当天完整收益。
- 明确交易价格、T+1可卖数量、停牌涨跌停、仓位上限和实际成交量约束。
- 同时报告毛/净收益、换手、最大回撤、基准和样本外结果;对滑点与费率做压力测试。
使用边界
- 简单shift(1)只解决部分时序问题;次日开盘成交还要区分隔夜和日内收益。
- 成本应按成交金额与买卖方向计提;0.15%是教学情景,不是统一市场费率。
背景 · 从一个困惑说起
「留最后两年做样本外」有个致命缺陷:你看过一眼样本外表现后忍不住回去调参——样本外被「用」了一次就脏了(研究污染)。更严重的是:两年的样本外只有一次判决机会,运气成分巨大。需要一种能反复产生「新鲜样本外」的协议。
由此产生的问题
走查验证的协议是什么?它如何做到「整个回测期都是样本外」?拼接净值怎么解读?
核心概念
Walk-Forward协议:滚动推进——用[2016-2018]训练→预测2019;再[2017-2019]训练→预测2020;…直到尽头;把各段「真样本外预测」拼成完整净值曲线。三个纪律:①每段的参数/模型只能用该段训练数据确定(连因子筛选、超参数都要在段内完成);②段与段之间不留任何「看过未来」的缝隙(含标签重叠的清洗,q-710的Embargo预告);③拼接净值的换手跨段处要计成本(参数变化引发的调仓)。解读:拼接曲线≈策略「如果当年真实运行」的成绩单——它仍有幸存者偏差(策略本身可能筛选过),但已是回测能给的最高诚实度。
为什么需要它
①把「一次判决」变「多次判决」:8段样本外≈8次独立考试,运气无法场场眷顾;②消灭研究污染:任何修改都要重跑全流程——修改成本高到让你三思;③ML时代的地基:阶段8的滚动训练(LightGBM选股)完全建立在这协议上——本题是它的先行基础。
实际应用场景
实现骨架:for end_year in range(2019, 2025): train=df[:end_year-1]; test=df[end_year]; model.fit(train); preds.append(model.predict(test));拼接preds→回测。段长选择:训练窗至少3-5年(覆盖风格切换)、测试窗1年。
与之前知识的联系
q-591定义了样本内外,本题给它装上时间轴;q-510的DSR从统计端防抽奖、走查从协议端防污染——两端合围;q-771(阶段8的OOS拼接)就是它+ML的完整实现。
⚠ 常见误解
- 拼接净值=实盘成绩:它仍隐含「策略大方向被选择过」的偏差(你为什么测这个策略?)——诚实度上限是回测的天花板
- 走查一次通过就高枕无忧:段数少时(3-4段)统计力不足;且市场结构变化(注册制)可让历史经验整体失效
- 段间可以微调参数(「就改一点」):任何跨段信息流动都是泄漏;改了就必须整段重跑——协议的价值正在于「改不动」
🛠 本题实践任务
把你的回测改造成走查版:按年滚动重估因子权重(哪怕只是IC加权),输出各年样本外超额。对比「全样本一份权重」的旧结果:差异就是「参数滞后」的真实成本。
💡 提示(先自己想5分钟再看)
最小改造:把权重计算包进年度循环;跨段第一天照常计调仓成本。
✅ 验收标准
逐年样本外超额表+新旧对比一句话。这份「六年真考试」的成绩单,是你目前能拿出的最硬证据。
在你的浏览器内运行。首次需联网下载 Python;支持标准库和 Pyodide 提供的 NumPy、pandas 等包。行情抓取、系统文件访问和部分第三方库请在本地环境运行。输出自检仅比对结果关键词,不代替逻辑审查。
Python · 独立工作线程 · 执行限时10秒
🤖 AI导师
导师会先检查你的前置知识(样本内外切分、参数重训、前视防御),再用案例、公式和代码帮助理解。此功能需要先启用服务。