ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

从异象到多因子模型:量化选股实战指南

从异象到多因子模型:量化选股实战指南 如果你在量化投资这个圈子里待过一阵子大概率绕不开这几个词异象anomalies、因子factors、多因子模型multi-factor models。这三样东西放在一起就是资产定价从“市场只有一个驱动因素”走到“收益由多个维度共同决定”的完整故事。异象是市场上反复出现、用传统理论解释不了的定价偏差因子是我们给这些偏差找到的度量维度多因子模型则是把这些维度组装成可以预测、可以交易、可以控制风险的体系。这篇文章写给正在研究因子策略的投研人员也写给刚接触量化选股、想知道论文里那些因子到底怎么用的朋友。我会从异象为什么会存在讲起一路拆解到因子构造、检验、合成和组合落地的完整流程中间穿插一些论文里不会写、但实战中非常容易踩的坑。1. 从异象到因子多因子模型到底在解决什么问题1.1 先搞清楚“异象”是什么我常跟人打一个比方如果有效市场假说和资本资产定价模型CAPM是对的股票的收益应该主要由它对市场组合的敏感程度也就是beta来决定。你去跑一个横截面回归把股票按市值、估值、过去涨幅这些特征分组组与组之间的收益不应该有系统性差异。但现实显然不是这样。从20世纪80年代开始研究者和从业人员不断发现一些“不该存在”的规律小市值股票长期跑赢大市值股票低估值股票跑赢高估值股票过去涨得好的股票在一段时间内继续涨波动率低的股票反而比波动率高的股票收益更高。这些用CAPM解释不了、但在多个市场多个时间段反复出现的规律就是异象。异象的本质是经验事实它是从数据里挖出来的统计规律不一定有理论支撑。规模效应、价值效应、动量效应、低波动率效应是后来被反复验证的几大经典异象。注意“被反复验证”这个前提很重要因为大量新发现的数据规律其实经不起推敲换个时间段、换个市场就不存在了。我在实际研究里判断一个异象是否值得认真对待通常会先看三个条件经济直觉能不能讲通、多个市场能不能重复、样本外数据是否稳定。三条都满足才谈得上进一步构造因子三条里缺一条那更多只是数据挖掘的噪音。1.2 因子模型给异象一个解释框架异象被反复验证之后学术界就面临一个尴尬问题如果市场是有效的这些超额收益到底从哪来最简单的解释是运气但动辄几十年的样本显然不能用运气糊弄过去。于是因子模型登场了。因子模型的本质是假设资产收益不是由一个共同因素决定而是由多个共同因素决定。每个因素就是一个因子我们通过回归估计出资产在每个因子上的暴露也叫因子载荷把期望收益分解为市场因子贡献、其他因子贡献和特质收益率三块。举个例子CAPM把股票收益写成市场因子的线性函数r_i - r_f beta_i * (r_m - r_f) e_i。这个模型只有一个解释变量。三因子模型则把它扩展成r_i - r_f alpha_i beta_i * (r_m - r_f) s_i * SMB h_i * HML e_i。SMB和HML就是两个新增因子分别代表小市值相对大市值、高账面市值比相对低账面市值比的收益差。加入这两项之后如果一组此前看起来“异常”的高估值、大市值股票alpha不再显著就说明它的超额收益可以用规模和价值因子来解释。这个过程很像做菜。收益率是一道菜的最终口感因子是食材因子暴露是配方比例。纯市场模型只承认一种食材多因子模型允许我们用多种食材去复现各种组合的收益特征。你越是能用一个包含少数因子的模型解释许多组合的收益差异这个模型的定价能力就越强也就越能让人相信异象不是“免费午餐”而是被模型捕获的某种系统性补偿。1.3 为什么是多因子而不是单因子或无限因子单因子模型最大的问题就是解释力不够。CAPM用beta解释收益解释不了规模、价值、动量这些截面规律只用一个价值因子又解释不了盈利能力强、投资风格保守的公司为什么往往跑赢。既然不同异象反映的是不同维度的定价逻辑想用一个模型同时解释它们就必须让多个因子同时进入定价方程这就是多因子模型的出发点。但多因子是不是越多越好理论上显然不是。因子过少会遗漏关键的定价维度因子过多则模型过拟合、因子之间高度共线、参数估计不稳定实盘里还会带来极高的换手和交易成本。学术界后来把几百个论文因子同时拿去做检验发现很多因子的显著性经不起多重检验的考验这就是“因子动物园”问题的由来。实务中我通常建议一个多因子组合最多容纳五到八个逻辑独立、经济含义清晰的因子就够了追求的是少而精不是大而全。多因子的累计收益曲线看起来很平滑但每多一个因子都会增加组合复杂度、容量约束和失效风险这三者的平衡只能靠自己在实盘中反复拿捏。2. 核心细节解析主流多因子模型的内功心法2.1 从CAPM到Fama-French三因子从一条直线到一个面要理解多因子模型绕不开Fama和French在1993年提出的三因子模型。他们在CAPM的基础上加入规模因子SMB和价值因子HML直接改变了很多人的研究范式。SMB的构造方法是每个月按市值中位数把股票分成大小两组再按账面市值比分成高、中、低三组取两两交叉得到六个组合小市值三组的等权平均收益减去大市值三组的等权平均收益就是SMB。HML类似是高账面市值比两组收益减去低账面市值比两组收益。这种双重排序构造法至今仍是标准做法核心目的是把规模和价值两个维度的信息互相控制住避免一个因子混入另一个因子的暴露。为什么是这两个因子Fama和French给出的解释是风险补偿小市值公司和账面市值比高的公司通常盈利更不稳定、财务杠杆更高、对经济下行更敏感因此承担了额外风险投资者要求更高回报。这个解释后续一直有争议但不管怎样三因子模型在实证上成功吸收了规模异象和价值异象把原本显著的alpha变成不显著。我自己的研究习惯里三因子模型至今仍是衡量策略是否“有真正超额”的基准很多所谓跑赢大盘的选股策略拆开看其实只是承担了较大的小盘或价值风格暴露并没有创造独立的alpha。2.2 五因子、q因子以及“因子动物园”三因子模型虽然经典但后来很多研究发现了它解释不了的新规律高盈利公司相对低盈利公司长期有超额收益投资扩张保守的公司相对激进扩张的公司也有超额收益。于是Fama和French在2015年把三因子上修为五因子加入盈利因子RMW和投资因子CMA。同一年代Hou、Xue和张橹基于q理论提出了包含市场、规模、投资、盈利四个因子的q因子模型后来扩展为q^5。这些模型表面都在追求同一件事用更少、更有理论基础的因子吸收更多类型的异象。“因子动物园”这个词形容的就是论文里因子数量爆炸的现象。从上世纪90年代到本世纪初研究者通过扫描数据发现了上百个能预测收益的因子从换手率到天气都能编成因子。这里面的水分很大很多因子换个样本期就失效。近十年的研究开始用严格的多重检验标准重新审视这些因子比如把显著性阈值从t值2.0提高到3.0甚至更高。我在实盘里对“新因子”的态度很简单如果没有清晰的经济逻辑、没有多市场样本外验证、没有完整的组合构建测试我不会轻易把它放进模型。因子不在多在真正独立且稳定。2.3 异象与因子的“打包”逻辑风险定价还是行为偏差异象和因子的关系本质上是一场关于“这些超额收益为什么存在”的路线之争。风险定价派认为异象是对系统性风险的补偿因子暴露越大承担风险越高期望收益越高。行为金融派则认为异象来自投资者的认知偏差比如过度反应、反应不足、处置效应、羊群效应错误定价会在长期慢慢修正而因子模型只是给错误定价贴了一个标签。这个争论对实操有直接影响。如果你相信风险定价那么因子在宏观承压时回撤就是正常的不应该因为短期回撤就砍掉因子反而应该把它当作风险预算来管理。如果你相信行为偏差那当市场信息效率提高、套利资本大量涌入时因子的alpha就会衰减甚至消失你需要持续监控因子的拥挤度和衰减速度。我的经验是经典价值因子和动量因子更像行为偏差驱动的收益来源它们的回撤有时长达五到十年这是所有依赖单一因子的人必须提前做好的心理建设和仓位准备。没有人能准确预言因子什么时候会恢复所以控制单因子暴露的上限比追求高收益重要得多。3. 实操过程与核心环节实现从一个异象到一个可用的多因子组合3.1 第一步数据准备与预处理理论最终要落到数据上。假设我们要在A股做一个覆盖全市场的多因子选股策略第一步是搭好底层数据。至少要三类数据行情数据包括收盘价、成交量、复权因子和涨跌停状态财务数据包括资产负债表、利润表和每个报告期的实际披露日期公司静态信息包括上市日期、行业分类、是否ST或PT。千万别小看这一步数据质量直接决定后续所有分析是否可信。这里最容易被忽视的是财报披露日期。很多人直接用财报报告期标签去关联数据比如拿2024年一季报的财务数值去预测2024年4月的收益但一季报可能要到4月30日才披露完这么做就引入了前视偏差。正确做法是维护一张“可得数据表”对每个调仓日只使用该日期之前已经实际披露的财报。另一个高频坑是复权因子处理计算收益率必须用后复权价格直接用原始价格会在分红除权日制造虚假跳空导致因子值和收益率错配。此外上市不足一年或长期停牌的股票应该提前剔除普通多因子策略一般也会剔除ST股避免财务风险事件带来的特殊扰动。数据预处理完成后还要确定调仓频率。多因子策略最常用的是月度调仓月频能平衡信号更新速度和交易成本也让财务数据的时效性对齐变得简单。日频或周频对数据细节和成本模型的精度要求更高新手容易吃亏。我现在的默认配置是月末最后一个交易日生成信号次月第一个交易日开盘执行估算成本时把开盘价和收盘价的价差、成交量冲击都考虑进去。3.2 第二步因子计算与标准化数据准备好之后开始构造因子。我用三个典型因子举例分别覆盖三类逻辑价值因子用账面市值比BP质量因子用净资产收益率ROE动量因子用过去12个月累计收益率剔除最近1个月也就是常用的12-1动量。先说价值因子。账面市值比的计算公式是“最近一期报告期末的股东权益除以当前总市值”。构建时要注意两点财报数据用最新可得报表滚动更新而不是固定年度账面市值比受行业影响很大银行地产和科技公司的绝对水平完全不可比必须做行业中性化处理。质量因子我习惯用过去四个季度ROE的均值也可以叠加毛利率、资产负债率构造复合质量因子用来反映公司盈利的真实性和持续性。动量因子相对直接用过去12个月的复权价累计涨跌幅但剔除最近一个月目的是避开短期反转效应和月度换仓的噪声。动量因子在多数市场都有明显效果但它在市场急跌后经常遭遇“动量崩溃”这一点在后面的问题排查章节会再展开。因子计算好之后绝对不能直接拿去打分合成。原始因子值存在三个问题量纲不同、极端值影响、与市值行业高度相关。因此需要三步处理。第一步去极值常见做法是MAD法或百分位数截尾我用中位数加减3倍MAD截断效果比固定分位数更稳健。第二步标准化把去极值后的因子值减去中位数再除以MAD或者直接用z-score让不同因子的量纲可比。第三步中性化把标准化后的因子对市值和行业虚拟变量做回归取残差作为新的因子值。中性化这一步很多人会跳过但如果不做你最终组合很可能在风格上过度暴露超额收益里有很大一部分其实是风格beta而不是因子独立的alpha。3.3 第三步因子检验——IC、分层回测因子构造完之后先别急着上组合要先检验它是否有真正的预测能力。我常用的检验手段有三个IC分析、分层回测和分组单调性检验。IC也就是信息系数指每个调仓期内因子值与股票下一期收益之间的横截面秩相关系数通常用Spearman相关。把历史每个月的IC算出来看IC均值、IC标准差、ICIRIC均值除以IC标准差、IC大于零的占比。经验门槛是IC均值绝对值在0.03以上ICIR在0.3以上IC胜率超过55%才值得继续跟踪。IC只能说明因子对收益排序有区分度不能说明经济意义上收益的大小所以还要配合分层测试来看。分层回测是一种更直觉的验证方式。把股票按因子值从低到高分成十组每组等权或市值加权构建组合每期调仓观察十组组合的累计收益是否单调递增或递减。单调性好的因子说明它对整条收益曲线都有分层能力如果只有最高组突出中间层次乱序那么这个因子的适用范围就要打折扣。分组单调性检验还可以在市值和行业子样本内重复做用来排除因子效果只是由少数行业或小市值股票驱动的假象。完整检验完一个因子得到的不只是一张收益表还包括它的换手率、容量特征和极端月份表现这些会直接决定它在多因子组合里能用多大权重。3.4 第四步因子合成与组合构建如果经过IC和分层回测后三个因子都有独立的预测能力下一步就是合成。最简单的合成方式是等权z-score相加先让每个因子都标准化成均值0、标准差1的z值再求平均得到综合得分。更进阶的做法是用因子过去一段时间的ICIR作为权重做动态加权让近几个月表现较好的因子在合成中获得更高权重。但动态加权要小心过拟合和换手率飙升我的建议是权重变化频率不要超过季度并且给每个因子设定权重上下限避免单一因子主导组合。综合得分算出来后按得分排序取得分最高的N只股票构建组合。权重可以用等权、市值加权也可以用风险平价或最大化组合对目标因子暴露的方式。最简单的起步方案是等权超额稳定但容量偏小市值加权容量大但对小盘因子的暴露会被稀释。组合构建还必须加约束单一行业权重不能超过基准的特定倍数或设上限单一个股占比不超过5%月度双边换手率控制在40%以内。这些约束看起来不起眼却决定了策略从回测走向实盘时永远不会因为集中度过高而暴跌也不会因为换手太频繁而被交易成本吃掉。3.5 核心代码逻辑简示下面给一个极简的多因子处理与选股流程代码不是可以直接上生产的版本但能帮你看清每一步的数据流关系。实测中我一般用Python配合pandas和numpy实现回测部分再用专门框架处理撮合与成本。import pandas as pd import numpy as np # price: 日频复权价宽表 # financials: 最新可用财报字段以披露日期为索引 # mktcap: 总市值 def winsorize(s, n3): med s.median() mad (s - med).abs().median() upper med n * 1.4826 * mad lower med - n * 1.4826 * mad return s.clip(lower, upper) def neutralize(s, industry, log_mktcap): X pd.concat([industry, log_mktcap], axis1) X pd.get_dummies(X, columns[industry]) X[const] 1 beta, _, _, _ np.linalg.lstsq(X.values, s.values, rcondNone) return s - X.values beta def factor_score(bp, roe, mom, industry, log_mktcap): bp winsorize(bp) roe winsorize(roe) mom winsorize(mom) z lambda s: (s - s.mean()) / s.std() bp_z z(neutralize(bp, industry, log_mktcap)) roe_z z(neutralize(roe, industry, log_mktcap)) mom_z z(neutralize(mom, industry, log_mktcap)) return (bp_z roe_z mom_z) / 3这段代码里winsorize函数用MAD法去极值1.4826是一个让MAD在正态分布下等价于标准差的换算系数。neutralize函数把因子对行业哑变量和对数市值做线性回归返回值是残差也就是剔除风格影响后的纯因子值。factor_score函数把去极值、中性化、标准化三个环节串起来最后等权合成综合得分。实际使用时要注意get_dummies生成的哑变量会在每个调仓期动态变化必须确保训练和预测阶段使用完全相同的中性化估计过程否则会造成信息泄漏。4. 常见问题与排查技巧实录4.1 因子失效是模型错了还是逻辑错了多因子策略最常遇到的困境不是一个因子突然归零而是连续几个月甚至一年多跑输。碰到这种情况第一反应不是急着砍因子而是先把归因做清楚。拆开收益来源看是风格beta拖累还是因子alpha贡献为负。如果是价值因子大幅回撤而组合里价值因子权重又很高那就属于风格回撤需要判断当前价值风格是否处于极端历史低位如果所有因子都在正常贡献但组合整体跑输那问题可能出在成本模型、调仓时点或权重计算上。我见过太多人因为三个月回撤就推翻整套模型然后反复调整参数结果越调越差。更合理的做法是提前制定因子失效预案例如ICIR连续12个月低于零且分层回测的前后两组收益差明显收窄才考虑暂停因子。暂停不是删除而是把它降权进行跟踪。另外因子的有效性是有生命周期的一个因子被公开之后会有越来越多的资金采用它超额收益会逐渐衰减。关键是你的因子是否有独特的信息来源或更精细的构造方式如果只是简单复刻一篇论文你的alpha生命周期基本取决于论文公开发表的时间。4.2 多重共线性与因子拥挤多因子模型里一个隐蔽的坑是多重共线性。价值和盈利因子之间往往正相关低波动和低杠杆因子也高度相关。如果你不做相关性检查就等权合成相当于在模型里把同一个信息重复计权好几次组合看起来更分散实际集中度反而更高。我在每次因子合成前都会计算因子之间的滚动相关矩阵相关系数超过0.6的因子会做去冗余处理比如保留历史IC更稳定的那个或者用PCA提取主成分这一步对组合稳健性的帮助极大。另一个相关问题是因子拥挤。当一个因子成为市场共识大量资金会沿着相同方向交易。因子多头组合对空头组合的波动率会被压低但在风格反转时会突然放大。判断拥挤度有一些简单的代理指标多空组合的换手率是否异常升高、因子收益的滚动波动率是否显著低于历史中枢、相关ETF或期货的持仓是否创出极端值。拥挤度很难精确度量但一个朴素常识是当大家都在说某个因子“永远有效”的时候通常就是它要回撤的时候。4.3 数据陷阱幸存者偏差、前视偏差与过拟合数据偏差处理是我认为比模型选择更重要的环节。幸存者偏差是最经典的问题如果你的股票池用的是“当前还在上市”的股票其实你隐含地排除了那些已经退市、被并购、因经营问题被清理的公司回测会系统性高估收益。A股历史上有大量中小市值股票退出市场不做幸存者修正的话小市值因子的回测效果会被大幅高估。解法很直接回测时必须使用当时时点的股票池包含后来退市的股票一直跟踪到它退市那个时点为止。前视偏差在前面财报披露日期的例子里已经讲过这里再补充一个常见场景指数成分股。如果你用指数成分作为股票池用的又是最新一期成分名单那你相当于用未来的信息做了选股。正确做法是使用指数在历史每个调仓日的真实成分名单这个数据看起来细枝末节但对回测真实性的影响非常大。最后说过拟合。多因子模型的参数空间其实很大因子构造窗口、去极值倍数、中性化方式、合成权重、调仓频率每一个变量都能微调出好看的曲线。想对抗过拟合一个有效方法是做严格的样本外验证把历史数据切成训练期和验证期训练期定参数验证期跑完整流程再进阶一点做滚动窗口递进式回测每期只用截至当期的数据做决策模拟真实的信息环境。4.4 实盘和回测的差距到底差在哪即使数据、因子、组合构建都做得非常严谨回测和实盘之间依然会存在差距。最大的差距来自交易成本。回测里双边换手20%看起来不高但实盘算上佣金、印花税、滑点和冲击成本年化损耗可能多出几个点。尤其中小市值股票冲击成本远高于大盘股这也是纯小市值因子策略在实盘里经常跑不过回测的核心原因。第二个差距是执行时滞。调仓信号在月末收盘后生成次月开盘执行中间隔了一个晚上再加集合竞价很多价格已经变化。如果信号对有涨跌停限制的股票特别敏感就会出现“想买买不进、想卖卖不出”的情况。所以我在组合构建时会设置个股最大权重和流动性过滤剔除日均成交额过低的股票。第三个差距偏心理层面回测曲线是事后的你知道它会涨回来所以对策略有信心实盘里每天看到净值波动很容易拿不住。我的解决办法是提前写投资逻辑说明书把因子为什么有效、历史最大回撤是多少、什么条件触发暂停都写清楚然后严格按文件执行而不是依据每日情绪调整。这一点听起来简单却是无数人失败的真正原因。最后分享一个我自己的体会。做了几年多因子模型我最深的感觉是模型本身从来不是核心竞争力真正难的是对每一个细节都保持较真财报日期有没有对齐、复权价有没有算对、中性化有没有做干净、因子之间有没有冗余。很多时候策略从平庸到优秀靠的不是找到什么神奇因子而是把上面这些基础工作做到位让每个因子的干净alpha都能稳定显现出来。如果你正在研究异象和多因子模型我的建议是先别急着堆因子先把一个模型的完整流程走通、走稳再慢慢扩展。这条路不性感但它是唯一靠谱的路径。
返回列表