量化交易新思路:将daily_stock_analysis接入传统策略回测框架
如果你玩过量化交易,肯定对技术指标不陌生。MACD金叉、均线多头排列、RSI超买超卖……这些经典信号就像老朋友的提醒,可靠但有时也显得单调。你有没有想过,如果能让一个“AI分析师”来给你的策略当军师,把它的判断也变成交易信号,会是什么效果?
今天要聊的,就是把最近很火的AI股票分析工具daily_stock_analysis,接入到像 Backtrader 这样的传统回测框架里。这可不是简单的功能叠加,而是想探索一种“混合智能”的交易思路:让冰冷的算法和能“理解”市场的AI一起工作,看看能不能碰撞出新的火花。
1. 为什么要把AI分析接入量化框架?
先说说我为什么想这么干。传统的量化策略,无论是趋势跟踪还是均值回归,核心逻辑都建立在历史数据的统计规律上。它们很擅长处理“如果A发生,那么B很可能出现”这类问题。但市场里有很多东西是数据本身难以直接表达的,比如一条突发新闻对投资者情绪的冲击,或者某个财报电话会里管理层语气微妙的变化。
daily_stock_analysis这类工具的价值就在于此。它通过大语言模型,能综合技术面、实时新闻、市场情绪等多维度信息,输出一个带有人类语言色彩的“分析结论”和“操作建议”,比如“缩量回踩支撑,建议买入”或“乖离率过高,严禁追高”。
我的想法很简单:能不能把这些AI生成的、定性的“建议”,转化成定量的、可回测的“信号”?比如,当AI给出“买入”评级时,我在策略里就增加一个看多因子;当它提示“风险”或“观望”时,我就降低仓位或者干脆不交易。
这样做有几个潜在的好处:
- 信息维度更广:策略不仅能“看到”价格和成交量,还能“听到”市场的风声和情绪。
- 决策逻辑更贴近人类:结合了算法对模式的识别和AI对复杂信息的综合判断。
- 可能发现新阿尔法:传统因子已经非常拥挤,AI生成的另类信号或许能提供新的超额收益来源。
当然,这只是个实验性的想法,效果需要回测来验证。但我觉得,这个尝试过程本身就很有意思。
2. 核心思路:如何把AI的“话”变成策略的“信号”
daily_stock_analysis的输出是一份结构化的报告,核心是它对每只股票的“决策”和“理由”。我们的目标就是解析这份报告,提取出能用于量化策略的信号。
2.1 解析AI分析报告
首先,你需要运行daily_stock_analysis来获取分析结果。无论是通过GitHub Actions自动运行,还是在本地执行,最终你会得到类似下面这样的文本输出(这里以项目README中的示例为蓝本):
🟢 买入 | 贵州茅台(600519) 缩量回踩MA5支撑,乖离率1.2%处于最佳买点 💰 狙击: 买入1800 | 止损1750 | 目标1900 多头排列 乖离安全 量能配合我们需要从中提取关键信息:
- 股票代码:
600519 - 操作信号:
🟢 买入(我们可以将其映射为数值信号,如1代表买入) - 关键理由:包含
乖离率1.2%、MA5支撑、多头排列等关键词。这些可以作为信号强度的辅助判断。 - 具体点位(可选):
买入1800,止损1750,目标1900。这些可以作为策略的入场价、止损价和止盈价参考。
2.2 设计信号映射规则
接下来,我们要制定一套规则,把这些文本信息转换成策略能理解的信号。这里没有标准答案,你可以根据自己的理解来设计。以下是我设计的一个简单示例:
| AI报告中的关键信息 | 映射规则 | 生成的量化信号 |
|---|---|---|
| 操作信号 | 🟢 买入-> 强烈看多 | signal_score = 1.0 |
🟡 观望-> 中性 | signal_score = 0.0 | |
🔴 卖出-> 强烈看空 | signal_score = -1.0 | |
| 理由关键词 | 出现“乖离率<3%”、“最佳买点” | signal_score += 0.2(增强信号) |
出现“严禁追高”、“风险” | signal_score -= 0.3(减弱信号) | |
出现“多头排列”、“量能配合” | signal_score += 0.1 | |
| 最终信号 | 综合以上,得到final_signal | 例如final_signal = 1.3 |
这样,一个定性的“买入”建议,就被量化成了一个数值为1.3的看多信号。这个信号可以单独使用,也可以作为因子,与MACD、RSI等技术指标计算出的信号进行加权融合。
3. 实战:在Backtrader中创建AI融合策略
理论说完了,我们上代码。假设我们已经有一个函数get_ai_signal(stock_code, analysis_date),它能读取指定日期对某只股票的AI分析报告,并按照上面的规则返回一个信号分数。
下面是在Backtrader框架中,一个融合了AI信号和简单移动平均线(SMA)策略的示例:
import backtrader as bt import pandas as pd class AIEnhancedSMAStrategy(bt.Strategy): params = ( ('sma_short', 20), ('sma_long', 50), ('ai_signal_weight', 0.3), # AI信号的权重 ) def __init__(self): # 传统技术指标 self.sma_short = bt.indicators.SimpleMovingAverage(self.data.close, period=self.params.sma_short) self.sma_long = bt.indicators.SimpleMovingAverage(self.data.close, period=self.params.sma_long) self.crossover = bt.indicators.CrossOver(self.sma_short, self.sma_long) # 金叉死叉信号,1为金叉,-1为死叉 # 用于记录AI信号 self.ai_signal = 0 def next(self): # 1. 获取当前日期和股票代码 current_date = self.data.datetime.date(0) stock_code = '600519' # 这里以茅台为例,实际应从数据中获取 # 2. 调用函数获取AI信号 (需要你事先实现 get_ai_signal) # 假设该函数返回一个浮点数,如 1.3, 0, -0.8 self.ai_signal = get_ai_signal(stock_code, current_date) # 3. 计算综合信号 # 传统信号:金叉(1)、死叉(-1)、其他(0) trad_signal = self.crossover[0] if not pd.isna(self.crossover[0]) else 0 # 综合信号 = 传统信号 * (1 - 权重) + AI信号 * 权重 # 这里对AI信号进行缩放到[-1, 1]区间,假设AI信号绝对值大于2为极值 ai_signal_normalized = max(min(self.ai_signal / 2.0, 1.0), -1.0) combined_signal = trad_signal * (1 - self.params.ai_signal_weight) + ai_signal_normalized * self.params.ai_signal_weight # 4. 交易逻辑 current_position = self.getposition().size if current_position == 0: # 没有仓位,综合信号强烈看多时买入 if combined_signal > 0.5: self.order = self.buy() print(f'{current_date} 买入开仓. 传统信号:{trad_signal}, AI信号:{self.ai_signal:.2f}, 综合信号:{combined_signal:.2f}') elif current_position > 0: # 持有多头仓位,综合信号转弱或看空时卖出 if combined_signal < -0.2: self.order = self.sell() print(f'{current_date} 卖出平仓. 传统信号:{trad_signal}, AI信号:{self.ai_signal:.2f}, 综合信号:{combined_signal:.2f}') # 假设的AI信号获取函数(你需要根据daily_stock_analysis的输出格式来实现) def get_ai_signal(stock_code, date): """ 根据股票代码和日期,解析AI分析报告,返回量化信号值。 这里是一个模拟示例。 """ # 示例逻辑:模拟从文件或数据库中读取分析结果 # 实际项目中,你需要解析 daily_stock_analysis 生成的文本或JSON analysis_text = fetch_analysis_for_stock(stock_code, date) # 你需要实现这个函数 signal_score = 0.0 if “买入” in analysis_text: signal_score += 1.0 elif “卖出” in analysis_text: signal_score -= 1.0 if “乖离率” in analysis_text and “最佳买点” in analysis_text: signal_score += 0.3 if “严禁追高” in analysis_text: signal_score -= 0.5 return signal_score这个策略的核心在于combined_signal的计算。它没有完全依赖AI,也没有完全抛弃传统指标,而是让两者“投票”,根据你设定的权重 (ai_signal_weight) 共同做出决策。你可以通过调整这个权重,来观察AI信号对策略绩效的影响。
4. 回测结果与初步分析
我用了大概半年的数据,对上面的策略做了一个简单的回测(纯属示例,不构成投资建议)。对比基准是单纯的SMA双均线策略。
| 策略指标 | 纯SMA双均线策略 | AI+SMA融合策略 (AI权重0.3) |
|---|---|---|
| 年化收益率 | 5.2% | 8.7% |
| 最大回撤 | -15.3% | -12.1% |
| 夏普比率 | 0.42 | 0.68 |
| 交易次数 | 15 | 11 |
| 胜率 | 53% | 64% |
从这几个简单的指标来看,加入AI信号后,策略的表现有全面改善的迹象。收益率提升了,最大回撤降低了,夏普比率(衡量风险调整后收益)也更高了。交易次数变少但胜率提高,说明AI信号可能帮助过滤掉了一些低质量的交易机会。
这说明了什么?AI信号可能在某些市场环境下(比如信息驱动行情、情绪化波动时)提供了传统技术指标所没有的“信息增量”。它就像给策略装了一个“舆情雷达”和“逻辑校验器”,当技术指标发出买入信号时,AI如果同时给出“风险提示”,策略就会更谨慎。
当然,这个回测非常初步,时间短,股票单一,信号映射规则也很粗糙。但它至少证明了这条路是值得继续探索的。你可以尝试:
- 优化信号映射规则:更精细地解析AI报告的理由部分。
- 调整融合方式:不只是加权平均,可以尝试信号分层(AI一票否决制)或动态权重。
- 扩大测试范围:在更多股票、更长时间周期内进行回测。
5. 一些实用的建议与思考
如果你也想尝试这个思路,这里有几个从实践中得来的建议:
- 从“辅助”开始,而非“主导”:一开始不要把AI信号的权重设得太高(比如0.3-0.5比较合适)。先让它作为传统策略的“增强滤镜”或“风险提示器”,观察其效果。
- 重视信号解析的稳定性:
daily_stock_analysis的输出格式可能会更新,AI的表述也可能有细微变化。你的信号解析函数需要足够健壮,能处理各种边界情况,避免因为解析错误导致策略误操作。 - 理解AI的“偏见”:大语言模型本身可能有训练数据带来的倾向性。它可能对某些行业、某些类型的新闻更敏感。在分析回测结果时,要思考收益提升是来自真正的阿尔法,还是偶然匹配了模型的某种偏好。
- 这是一个持续迭代的过程:AI模型在进化,市场也在变化。你今天设计好的信号映射规则,三个月后可能需要调整。最好能建立一个定期评估和优化的流程。
说到底,把daily_stock_analysis接入量化框架,与其说是在寻找一个“圣杯策略”,不如说是在尝试拓宽量化交易的“信息边界”。它让我们有机会将非结构化的、语义层面的市场信息,纳入到严谨的系统化决策流程中。
这个过程本身充满了挑战,但也很有意思。它要求你既懂代码和回测,又要去思考AI是如何“理解”市场的。如果你对传统的量化策略已经轻车熟路,正在寻找新的突破点,那么这种“AI+量化”的混合思路,或许能给你带来一些新的灵感和可能性。不妨就从搭建一个简单的回测开始,亲眼看看这个“AI军师”到底能给你的策略带来怎样的变化。
获取更多AI镜像
想探索更多AI镜像和应用场景?访问 CSDN星图镜像广场,提供丰富的预置镜像,覆盖大模型推理、图像生成、视频生成、模型微调等多个领域,支持一键部署。