股票因子缺值如何改变组合:比较跳过、保留旧值与退出持仓
因子值缺失应进入明确决策政策,不能静默变成零分,也不能让旧值永久有效。保存最后可用分数及年龄,先判断资格,再把目标变化推进到卖出、替换买入与成本。交付物是逐日状态账,不只是某个文件缺了多少单元格。相同的缺失面板可以产生不同持仓路径,因此政策必须先于结果确定。
本指南比较立即排除、有限复用和无限复用,使用同一组虚构美股及美元账户。观察、价格与权益全部合成,CoTrading覆盖检查能力仍为规划或待核实。本方法不补造尚未披露的基本面,也不声称数据服务能够恢复从未可得的历史。验证重点是缺失状态如何改变交易。
把原观察与当前状态分开
每条观察保留证券标识、分数、来源时间、可得时间及首次可用交易期。新输入缺失只表示没有新观察,不应抹去旧值血缘。保留新输入状态和被复用旧值,后来检查者才能区分新更新、沿用和真正没有任何记录。如果只剩一列填满的数字,这些差别就消失了。
明确区分新鲜、可复用旧值、过期、从未观察四种状态,不能全部编码成零。真实零可能有经济含义并进入排序,未知值没有这个信息。Python数学模块文档说明了有限数检查,可用于拒绝非数值与无穷;但缺失仍需独立状态,不能仅用数值过滤代替政策。
可执行政策把None、NaN、正无穷和负无穷都视为不可用新观察,不覆盖最后有限分数,也不刷新年龄。旧有限值在有效期内仍可复用;A从未提供有限值时,年龄为null、状态为never_observed,不能入排序。账本分别输出score_status与数值年龄,不为尚无观察的股票编造起点。
本例年龄按市场交易期索引计算:当前期减最后可用观察期。周末与节假日不额外消耗交易期年龄。若实际政策按自然小时,应另设时钟并测试,不能一列年龄有时按天、有时按交易日。尤其披露间隔较长的基本面与每日价格因子,不应无解释使用同一个有效期。
先冻结三种资格政策
立即排除只接受年龄零;有限复用接受零或一;无限复用故意作为弱反例,不限制最后分数年龄。三种都对合格股票按分数降序选一只,同分按稳定证券标识决胜。没有根据最终收益搜索阈值,也不把缺值填零后混入正常候选。
有限政策下,已持有但过期的股票失去资格,在下一给定可执行开盘卖出,有其他合格最高分就替换,没有就保留现金。若退出缺行情,则需要另设退出阻止状态;本例每笔请求都提供开盘,不能声称该分支已经测试。目标归零本身不表示真实数量已经归零。
SEC官方EDGAR接口说明区分财务事实与申报上下文,因此使用披露因子时应保留来源与可得信息。它没有规定一交易期有效;这个门槛是本例作者政策,不能当监管要求,更不能直接推广给其他因子。合成测试仅证明政策按声明执行。
手算四个决策期
第零期A九分、B八分。第一与第二期A新输入缺失,B每期更新八分。第三期A更新十一,B仍新鲜八。每条观察都假设在对应给定执行开盘之前可得,不使用该期开盘之后的收盘生成当天订单。这个信息时序前提必须随数据一起交付。
最大年龄一时,第零期选A,第一期A年龄一仍保留,第二期年龄二被排除、改选B,第三期新值重置A年龄零、重新选A。序列为A、A、B、A。第一期缺观察没有自动交易,第二期过期才引发交易;这两个状态是验收时应分别抽查的行。
立即排除得到A、B、B、A;无限复用得到A、A、A、A。全部来自同一输入,不同处只在资格政策。后来十一分不能回填到A缺失的两期,否则就删除了本任务本来要研究的信息短缺。晚到与修订应追加版本,不覆盖原来真实可见状态。
有限复用账户逐笔闭合
初始资金一千,每次持仓四十股,每笔执行费为虚构的一。第零期开盘两股均十,买A金额四百加费一,剩五百九十九,同开盘估值权益九百九十九。初始减少一来自费用,不是因子已经产生负收益。数量和费用分别写账,避免只留一条净值。
第一期开盘A十点二、B十,继续四十股A,没有新单和新费。权益为五百九十九加四百零八,等于一千零七。第二期A十一、B十,卖A四百四十减一,再买B四百加一,现金六百三十七,持仓价值四百,权益一千零三十七。
第三期B十点五,卖四十股净收四百一十九;A十二,买四十股连费四百八十一。现金五百七十五,A价值四百八十,权益一千零五十五。总共五张订单、五个单位费用。最后仍有持仓,因此这不是最终清仓现金,若要求变现还需另给退出价及费用。
用另外两政策核验不同机制
立即排除第一期就按十点二卖A并进入B,最后现金五百四十三,估值权益一千零二十三。它同样是五张订单,差异主要来自替换时间与价格路径,不能凭直觉写成一定多付了两次费用。费用数必须从实际订单数重算,不能由缺失天数估计。
无限复用只付最初买入费,最后现金五百九十九,加A价值四百八十,权益一千零七十九。这个人为结果更高,不证明政策有效。第二期它读取了有限政策认为过期的旧分数。如果因为这个结果好就改用无限复用,资格规则就变成事后收益选择,不再是独立数据政策。
这也说明缺值处理不能只做表格美化。连续填满旧分数会让排序和曲线看起来平滑,却可能把来源中断隐藏很久。报告必须显示复用比例与最老年龄,不能只说“没有缺值”。输入是否齐全、资格是否有效与账户是否可交易,应分别判断,不能由其中一个布尔状态统领。
执行逐期状态账
下载完整示例,保存为R564.py,用Python 3.12及以上运行python R564.py。仅用标准库与合成数据,源文件位于docs/growth/research/round-5/examples/R564.py。输出有限政策每期年龄、候选、目标、订单、现金和权益。
断言检查三套目标序列、第二期A失去资格、卖A买B的对应订单,以及三种期末值。不要只查最终又持有A,因为错误实现即使漏掉中间B持仓,也可能在最后显示同一证券。检查旧值仍合法的一期,再检查刚过期的一期,才能覆盖真正状态转移。
新增断言把A两次缺更新分别换成NaN、正无穷、负无穷,均要求同一A/A/B/A路径、候选全有限、年龄零/一/二/零,以及现金五百七十五、权益一千零五十五。若A首期就无观察,选择B且A年龄为空;若首期全池都缺,目标为空,不造分数、订单或费用,现金与权益仍一千。这些边界均实际执行,不由正常路径推断。
复核时以期末数量承接下一期,而不是根据填补后分数重新假想历史持仓。替换卖出若失败,现金不会自动释放;本例没有这个分支,所以不把它描述成已经具备真实停牌处理。实际扩展要补一个卖出失败样本,再检查买入是否因资金不足而被取消,保持因果链可见。
更新契约与完成条件
配置中保存最大年龄、年龄时钟、替换规则和已有持仓处置。每期统计新鲜、复用、过期与从未观察数量。新鲜突然大量变复用,可能暴露数据管线中断,即使排序和净值仍流畅。指标应帮助发现输入异常,不能用曲线连续来证明数据可靠。
迟报到达时保留原始出处,只从真实可得时点应用。区分旧事实修订与新报告期测量;二者可能有相同下载时间,却不是同一经济事件。保存旧运行,变化才可归因到资格、更新或来源修订,不被笼统称为因子变好。未验证的执行限制持续列在输出旁。
完成条件是每个缺失观察都能沿分数年龄走到资格、持仓和现金。另一个实现者应能只靠四期输入与政策重建同一路径,不需猜测空白是什么意思。扩大真实样本前先做到这一点,再讨论收益、覆盖稳定性和参数适用范围,避免用一个表现最好的填补结果代替事先研究设计。
交接时复核年龄起点
年龄起点是按政策首次可使用时刻,不自动等于财务期末或下载日期。本例第三期新值假设开盘前可用;若现实更新盘后才来,就不能重置更早成交的年龄,必须把首个允许期向后安排。按报告期末计年龄可能把刚披露事实误判过期,按今天下载计又可能让很旧事实假装新鲜,两个方向都要避免。
把保留值行与来源事件行并排。九分年龄一与新报告九分数值相同、排名也相同,却不是同一资料状态。它们影响中断识别、修订处理和为何继续持仓的解释。从未观察的股票单列,不能编一个初始旧分数填进去。后续新增覆盖先获得真实输入,再开始年龄计数,不能从缺失面板推造历史。
接手者抽查每期年龄与实际订单,尤其查看第二期退出是否真由过期触发,而非程序把空白自动当负信号。原因准确,才可讨论下一版门槛;若连状态来源都不清楚,调整有效期只会掩盖缺陷。这个交接检查保持信息政策与代码含义一致,不把看起来连续的数字列误当连续可用事实。
常见问题
缺分数可以填零吗?
只能作为另行声明、有依据的插补规则;零不是未知信息的中性表示。
期末值最高的政策就是最好吗?
不是。应先确定信息与交易契约,再观察结果。