虽然看起来用了相关性选择行业ETF,实际上选择出来的还是行业ETF轮动,很普通,多此一举
这个策略的核心逻辑是通过 “趋势筛选→相关性最小化→趋势质量评分” 三步筛选,最终确定目标持仓并调仓,各环节存在明确的先后依赖关系。以下是具体逻辑和依赖关系的拆解:
策略的核心目标是从初始 ETF 池中,筛选出 “趋势良好、相关性低、趋势质量适中” 的品种进行轮动。整体流程由trade函数主导,依次调用三个关键函数,形成 “输入→处理→输出” 的依赖链:原始 ETF 池 → 趋势筛选 → 相关性最小化筛选 → 趋势质量评分 → 调仓
2. 第一步:趋势筛选(get_trend_length函数)【比如黄金和纳斯达克长期上涨,把长涨多跌少的选出来】
作用:从原始 ETF 池中筛选出 “长期维持多头趋势” 的品种,作为后续筛选的基础池。
逻辑:
获取过去 3500 天的收盘价数据;
计算每个 ETF 的 “短期均线(10 天)在长期均线(30 天)上方的天数占比”(通过count_days_above函数实现);
保留占比 > 3 的 ETF(即多头趋势持续时间足够长的品种)。
输入:原始 ETF 池(g.etf_pool);
输出:趋势达标的 ETF 列表(第一阶段候选池);
依赖:无前置筛选,直接基于原始池计算,是整个流程的 “起点筛选”。
3. 第二步:相关性最小化筛选(min_corr函数)【避免选入沪深300,上涨50 这样相关性系数高的ETF】
作用:从趋势达标的 ETF 中,选出 “两两相关性最低” 的前 4 只,降低持仓组合的系统性风险。
逻辑:
获取过去 243 天(约 1 年)的收盘价,计算对数收益率(消除价格量级影响);
计算收益率的相关系数矩阵,统计每个 ETF 与其他 ETF 的相关系数绝对值的平均值;
按平均值从小到大排序,取前 4 只(相关性最低的品种)。
输入:第一步筛选后的趋势达标 ETF 列表;
输出:相关性最小的前 4 只 ETF(第二阶段候选池);
依赖:必须基于第一步的趋势达标池,仅对 “趋势好” 的品种计算相关性,避免纳入趋势差的品种。
4. 第三步:趋势质量评分(get_rank函数)【这里还是斜率*R平方的方式动量打分】
作用:对相关性最低的 4 只 ETF,进一步筛选 “趋势强度和稳定性适中” 的品种。
逻辑:
对每只 ETF,用过去 25 天(g.m_days)的收盘价对数,与时间(天数序号)做线性回归,得到斜率(代表趋势强度)和 R 平方(代表趋势稳定性);
计算score = 年化收益率 × R平方(综合趋势强度和稳定性);
筛选score在 - 0.5 到 4.5 之间的 ETF(排除趋势过强或过弱的品种),并按score降序排序。
输入:第二步筛选后的相关性最小的 4 只 ETF;
输出:评分达标的 ETF 排序列表(目标持仓候选);
依赖:必须基于第二步的低相关性池,仅对 “低相关 + 趋势好” 的品种评估趋势质量,确保最终持仓兼顾分散性和趋势合理性。

原始ETF池(g.etf_pool)
↓(输入)
get_trend_length(趋势筛选)→ 趋势达标池
↓(输入)
min_corr(相关性最小化)→ 低相关性前4池
↓(输入)
get_rank(趋势质量评分)→ 目标持仓列表
↓(输入)
trade(调仓)→ 完成持仓更新
发表评论:
◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。