问题描述
/
解决方案
在 ptrade 量化平台中,分钟级别策略(frequency='1m' 等)由于每个交易日需要执行 240 次 handle_data,数据量和计算量是日线策略的数百倍,因此回测速度自然会慢很多。如果策略中存在低效的数据获取或计算逻辑,回测时间会被进一步拉长。
以下是提升 ptrade 分钟级别策略回测速度的几个核心技巧:
1. 开启 is_dict=True 加速数据获取
ptrade 的多个行情获取接口(如 get_history、get_price、get_individual_entrust、get_individual_transaction)都支持 is_dict 参数。默认情况下,这些接口返回 pandas.DataFrame 或 Panel 对象,构建这些对象需要消耗较多时间。
优化方法:将 is_dict 设置为 True,接口将返回原生的 Python 字典(dict)或 OrderedDict,取数速度会有大幅提升。
# 优化前:返回 DataFrame,速度较慢
his_df = get_history(10, '1m', 'close', security_list=g.security)
# 优化后:返回 dict,速度极快
his_dict = get_history(10, '1m', 'close', security_list=g.security, is_dict=True)
2. 精简股票池(Universe)
handle_data(context, data) 中的 data 参数包含了股票池中所有标的当前周期的行情数据。如果你的股票池(通过 set_universe 设置)包含了大量不需要交易的股票,框架在底层准备这些数据时会浪费大量时间。
优化方法:仅将真正需要监控和交易的标的放入 set_universe 中。如果需要动态调整,可以在 before_trading_start 中更新股票池。
3. 减少 handle_data 中的重复计算和 API 调用
handle_data 每分钟都会被调用,任何耗时的操作都会被放大 240 倍。
优化方法:
- 盘前预处理:将不需要每分钟更新的数据(如财务数据
get_fundamentals、股票基础信息get_stock_info、日线级别的历史数据等)移到before_trading_start中获取,并存入全局变量g中。 - 避免全量拉取:不要在每分钟都拉取过去很长一段时间的分钟 K 线,尽量只获取计算指标所需的最小 K 线数量(
count)。
4. 谨慎使用日志打印(log.info)
在分钟级别回测中,如果每分钟都打印多条日志,大量的 I/O 操作会严重拖慢回测进度。
优化方法:在回测阶段,尽量注释掉不必要的 log.info 或 log.debug,仅在触发交易信号或发生异常时打印日志。
5. 避免多线程接口冲突
官方文档指出,get_history 与 get_price 接口不支持多线程同时调用。如果在 run_daily 或 run_interval 等定时函数中,与 handle_data 同一时刻调用这些接口,不仅可能导致数据获取为空,还可能引发底层阻塞,影响速度。
优化方法:合理错开定时任务的时间,避免与 handle_data 的执行时刻(每分钟的整点)完全重合。
通过以上优化,特别是使用 is_dict=True 和将日频数据获取移至盘前,通常可以显著缩短分钟级别策略的回测时间。