ta / 批量特征工程

add_all_ta_features 一次加 86 列:能拿到什么、会丢掉什么

add_all_ta_features(df, open="open", high="high", low="low", close="close", volume="volume") ——这是 ta 最常被引用的那一行。本机实测:5 列输入进去,91 列出来, 新增 86 列,覆盖 43 个指标类中的 42 个。

但它有三个不写在 README 里的开关:窗口全部硬编码在 wrapper 里(没有 window 参数)、 vectorized=True 会静默少 18 列、 默认 fillna=False 时 400 行里没有一行是完整的。这一页把三条都量出来。

5 列进 91 列出新增 86 列覆盖 42/43 个类核验 ta 0.11.0
输入 5 列open / high / low / close / volume
五个子函数add_volume / volatility / trend / momentum / others
输出 91 列新增 86 列,覆盖 42 个指标类
两个开关fillna 决定 NaN,vectorized 决定少 18 列
依据 ta/wrapper.py 源码与本机实测(86 列清单来自实际列名)整理的执行链路示意;非官方功能图。

函数契约

add_all_ta_features 的参数分别起什么作用

参数默认值作用注意点
df—输入 DataFrame函数原地改传入的对象并返回它;保险做法是传 df.copy()
open/high/low/close/volume—五个列名字符串必须与 DataFrame 列名完全一致(区分大小写)
fillnaFalse传给每个指标的开关True 时窗口不满也算,头部数值含义不同(见预热与 NaN 页)
colprefix""给所有新列加统一前缀已有 momentum_ 这类模块前缀,再加一层可读性会下降
vectorizedFalse只使用「向量化」指标不是加速开关,是「少算 18 列」的开关——见下节
没有 window—无法通过这个函数调整任何窗口要自定义窗口必须绕过 wrapper,直接实例化指标类

最容易误解的是 vectorized:README 与文档字符串只说「if True, use only vectorized functions indicators」,听起来像性能选项。实际效果是 wrapper 里 if not vectorized: 包裹的代码块被整体跳过,结果是少了 18 列。用它之前先确认你要的列还在。

输出列清单

add_all_ta_features 到底新增了哪些列:86 列清单

模块来源列数新增列名(去掉模块前缀)
成交量ta.volume10adi、obv、cmf、fi、em、sma_em、vpt、vwap、mfi、nvi
波动率ta.volatility21bbm、bbh、bbl、bbw、bbp、bbhi、bbli、kcc、kch、kcl、kcw、kcp、kchi、kcli、dcl、dch、dcm、dcw、dcp、atr、ui
趋势ta.trend34macd、macd_signal、macd_diff、sma_fast、sma_slow、ema_fast、ema_slow、vortex_ind_pos、vortex_ind_neg、vortex_ind_diff、trix、mass_index、dpo、kst、kst_sig、kst_diff、ichimoku_conv、ichimoku_base、ichimoku_a、ichimoku_b、stc、adx、adx_pos、adx_neg、cci、visual_ichimoku_a、visual_ichimoku_b、aroon_up、aroon_down、aroon_ind、psar_up、psar_down、psar_up_indicator、psar_down_indicator
动量ta.momentum18rsi、stoch_rsi、stoch_rsi_k、stoch_rsi_d、tsi、uo、stoch、stoch_signal、wr、ao、roc、ppo、ppo_signal、ppo_hist、pvo、pvo_signal、pvo_hist、kama
其他ta.others3dr、dlr、cr

合计 86 列,覆盖 42 个指标类。43 个类里只有 WMAIndicator(加权移动平均)没有对应的新增列——wrapper 里根本没有引用它;另外 SMA 与 EMA 各只给了 fast(12) / slow(26) 两列,没有「单一均线」列。想用 WMA 或别的窗口,必须直接调类。完整列名清单来自本机 add_all_ta_features 的实际输出,不是从文档抄的。

vectorized 开关

vectorized=True 会静默去掉哪些列:18 列明细

被移除的列所属区块为什么影响
volatility_atr、volatility_uiadd_volatility_ta 的 if not vectorized: 块这两个实现在 wrapper 作者看来不是「向量化」写法ATR 和 Ulcer Index 直接消失
momentum_kamaadd_momentum_ta 的同类代码块同上KAMA 自适应均线消失
volume_mfi、volume_nviadd_volume_ta 的同类代码块同上MFI 与 NVI 消失
trend_adx、trend_adx_pos、trend_adx_negadd_trend_ta 的同类代码块同上趋势强度三列全丢
trend_cci、trend_aroon_up/down/ind同上同上CCI 与 Aroon 全丢
trend_psar_up/down/_indicator(共 4 列)同上同上PSAR 全丢
trend_visual_ichimoku_a、_b同上同上仅失去「视觉」两条线,基础 Ichimoku 仍在

实测总计移除 18 列:86 → 68。值得注意的分布是:被移除的全是「非向量化实现」的那一批,其中包含 ATR、ADX、CCI 这些在实盘里用得最多的指标。如果你的特征表里少了它们,先检查是不是把 vectorized 打开过。

硬编码窗口

wrapper 里的窗口怎么设置:是写死的还是可调的

模块指标(列名)窗口(源码里写死的值)
成交量volume_fi / volume_em / volume_vwap / volume_mfi13 / 14 / 14 / 14
波动率volatility_bbm…bbp20,宽度 2 个标准差
波动率volatility_kcc…kcli10
波动率volatility_dcl…dcp20(offset = 0)
波动率volatility_atr10(不是常见的 14)
波动率volatility_ui14
趋势trend_macd* / trend_ppo* / trend_pvo*26 / 12 / 9
趋势trend_sma_fast / trend_sma_slow12 / 26
趋势trend_ema_fast / trend_ema_slow12 / 26
趋势trend_vortex_* / trend_trix / trend_dpo / trend_adx* / trend_cci / trend_aroon_*14 / 15 / 20 / 14 / 20 / 25
趋势trend_mass_indexfast 9 / slow 25
趋势trend_kst*ROC 周期 10 / 15 / 20 / 30
趋势trend_ichimoku_* / trend_visual_ichimoku_*9 / 26 / 52
趋势trend_stcslow 50 / fast 23 / cycle 10 / smooth 3 与 3
趋势trend_psar_*step 0.02 / max_step 0.20
动量momentum_rsi / momentum_stoch_rsi* / momentum_stoch* / momentum_wr14(WR 用 lbp=14)
动量momentum_tsislow 25 / fast 13
动量momentum_uo7 / 14 / 28
动量momentum_ao5 / 34
动量momentum_roc12(不是 RSI 那样的 14)
动量momentum_kama10,pow1 = 2、pow2 = 30

这张表来自 ta/wrapper.py 的源码逐行扫描,不是默认参数表。重点是两件事:①add_all_ta_features 没有 window 参数,所有窗口写死在函数体里;②写死的值与类本身的默认值并不总是一样——例如 AverageTrueRange 类的默认窗口是 14,但 wrapper 里写的是 10;ROCIndicator 类默认 12,wrapper 也是 12;KAMAIndicator 类默认 10,wrapper 也是 10。所以「用类」和「用 wrapper」得到的是不同参数下的结果。

fillna 与可用行

算完 86 列之后还剩多少可用样本

指标实测结果原因
fillna=False(默认)下完整行数0 / 40086 列里最长预热 47 行,且 psar_up 一列就有 212 行 NaN——没有一行能让全部列都有值
fillna=True 下完整行数400 / 400窗口不满也算,NaN 被消除
fillna=True 下 NaN 单元格总数0同时 inf 数量也是 0(_check_fillna 会把 ±inf 替换成 NaN 再前向填充)
fillna=False 下 NaN 最多的列trend_psar_up(212 行)PSAR 的上趋势标记本身是稀疏的
fillna=False 下无 NaN 的列数19 列含 ATR、ADX、Keltner、OBV 等——但它们可能是 0 值表头
对输出调用 ta.utils.dropna()0 行每一行都有 NaN,dropna 会全部删掉

所以「用 fillna=False 还是 True」不是风格问题,而是取哪一头:要么接受「没有一行是完整的」,自己按最长的预热裁剪;要么接受「头部数值是用不完整窗口算出来的」。官方 README 的示例用的是先把原始数据 dropna,再 add_all_ta_features——顺序不能颠倒,否则会把数据集清空。每个指标的预热长度见预热窗口页的实测表。

筛选建议

86 列太多用不完,该按什么顺序筛

拿到 86 列之后该怎么筛(推荐顺序)

  1. 先按模块删掉重复表达:布林带贡献 7 列、Donchian 5 列、Keltner 7 列、Aroon 3 列、Ichimoku 4 列——同族列高度相关,保留代表性的 1–2 列即可。
  2. 再按预热长度设起点:psar_up(212 行 NaN)、psar_down(190 行)这类稀疏列要么单独处理,要么直接删。
  3. 然后处理零值表头:把 volatility_atr、trend_adx 这些表头为 0 的列按窗口切片或替换成 NaN。
  4. 最后才谈相关性筛选:全部列都来自同一份收盘价,彼此高度共线;先用业务逻辑(量 / 价 / 波动 / 趋势)分组,再用统计方法去冗余。
  5. 把这次的选择写下来:列名、窗口、删掉的原因——下次升级依赖时才能判断「数值变化」是数据问题还是列变了。

如果目的是「快速看一眼」而不是「建特征表」,更省事的做法是先只算 2–3 个指标(例如 RSIIndicator + BollingerBands + AverageTrueRange),确认口径后再扩到全量。

FAQ

关于 add_all_ta_features 的常见问题

add_all_ta_features 会改我的原始 DataFrame 吗?
会。它把新列直接写在传入的 DataFrame 上并返回同一个对象。本站在所有实测里都传 df.copy()。如果你还要用原始表做别的计算,务必在调用前复制一份。以官方实现为准。
为什么我加出来的列数不是 86?
先检查两个开关:①vectorized=True 会少 18 列(86 → 68);②colprefix 只是加前缀,不改变列数。如果列数仍然不对,确认 ta 的版本与你参考的资料一致(本站实测为 0.11.0)。
能不能用 add_all_ta_features 指定窗口,比如 RSI 用 7 而不是 14?
不能。这个函数没有 window 参数,wrapper 里所有窗口都是写死的常量。要自定义窗口必须绕过它,直接实例化指标类,例如 RSIIndicator(close=df["close"], window=7).rsi()。
为什么 ATR 列算出来和我单独调类的结果不一样?
因为窗口不同。add_volatility_ta 里写的是 window=10,而 AverageTrueRange 类自己的默认值是 14。本站实测:同一份数据下两者的前 13 行分别是 9 个 0 与 13 个 0,最大绝对差 1.26636756。要对齐就必须显式传窗口。
86 列能不能直接喂给机器学习模型?
技术上可以,但要先处理三件事:①fillna=False 时没有一行是完整的(实测 0/400);②同族列高度共线;③部分列是 0/1 标记列,不是连续量。本站只说明列的产生方式与口径,不提供建模方案。
add_all_ta_features 支持多标的(面板数据)吗?
不支持。它按单个 DataFrame 的列处理,没有标的维度的概念。多标的要么循环调用(会明显变慢),要么自己按标的 groupby 后分别计算。README 的 TODO 里也提到「用 Pandas 多级索引同时算多个指标」尚未实现。
为什么输出里有些列全是 0 或全是 1?
那是标记列,不是指标值。例如 volatility_bbhi、volatility_kchi、trend_psar_up_indicator 这类以 _indicator 结尾的列,取值只有 0 和 1,表示「是否触发」。本站实测这类列在样本前 20–30 行全是 0,属于正常现象。

接下来读哪一页?

特征列有了,但「有特征」不等于「能评估策略」。回测边界页把指标到策略之间必须补齐的步骤逐条拆开。