3 分钟快速生成代码
输入想法,AI 即刻生成可运行代码
这是一个基于 QMT (Quant Trader) 平台的价值投资策略示例。
# -*- coding: gbk -*-
import pandas as pd
import time
def init(ContextInfo):
"""
初始化函数,策略启动时执行一次
"""
# 1. 设置策略参数
ContextInfo.stock_num = 10 # 持仓股票数量
ContextInfo.index_code = '000300.SH' # 股票池:沪深300
ContextInfo.last_month = -1 # 用于记录上一次调仓的月份
# 2. 设置账号(回测模式下通常默认为 'test',实盘请修改为真实资金账号)
ContextInfo.accid = 'test'
ContextInfo.set_account(ContextInfo.accid)
print("策略初始化完成,开始运行价值投资策略...")
def handlebar(ContextInfo):
"""
行情事件函数,每根K线执行一次
"""
# 获取当前K线的时间
bar_index = ContextInfo.barpos
timetag = ContextInfo.get_bar_timetag(bar_index)
current_date_str = timetag_to_datetime(timetag, '%Y%m%d')
current_month = int(current_date_str[4:6]) # 提取月份
# --- 1. 调仓时间控制 (月度调仓) ---
# 如果当前月份与上一次调仓月份相同,则跳过,不进行操作
if current_month == ContextInfo.last_month:
return
# 更新调仓月份标记
ContextInfo.last_month = current_month
print(f"=== 检测到新月份 {current_date_str},开始执行选股调仓 ===")
# --- 2. 获取股票池 ---
# 获取沪深300成分股
stock_list = ContextInfo.get_sector(ContextInfo.index_code)
if not stock_list:
print("获取成分股失败或为空")
return
# --- 3. 获取因子数据 (PE 和 PB) ---
# 注意:根据QMT文档,因子字段需使用英文名
# Valuation_and_Market_Cap.PE : 市盈率
# Valuation_and_Market_Cap.PB : 市净率
factor_fields = ['Valuation_and_Market_Cap.PE', 'Valuation_and_Market_Cap.PB']
# 获取当天的因子数据
# 返回格式:pandas.DataFrame index=代码 ,columns=字段
factor_data = ContextInfo.get_factor_data(
factor_fields,
stock_list,
current_date_str,
current_date_str
)
if factor_data.empty:
print("未获取到因子数据")
return
# --- 4. 数据清洗与选股逻辑 ---
df = factor_data.copy()
# 4.1 去除空值
df.dropna(inplace=True)
# 4.2 剔除亏损股 (PE <= 0)
df = df[df['Valuation_and_Market_Cap.PE'] > 0]
# 4.3 按照 PE 从低到高排序 (价值投资核心)
df.sort_values(by='Valuation_and_Market_Cap.PE', ascending=True, inplace=True)
# 4.4 选取排名前 N 的股票
target_stocks = df.head(ContextInfo.stock_num).index.tolist()
print(f"本期选中股票 ({len(target_stocks)}只): {target_stocks}")
# --- 5. 执行交易 (等权重) ---
if len(target_stocks) > 0:
target_weight = 1.0 / len(target_stocks) # 单只股票目标仓位权重
# 5.1 卖出不在目标列表中的持仓
# 获取当前持仓
positions = get_trade_detail_data(ContextInfo.accid, 'stock', 'position')
current_holdings = [obj.m_strInstrumentID for obj in positions]
for stock in current_holdings:
if stock not in target_stocks:
# 目标权重设为0,即清仓
order_target_percent(stock, 0, ContextInfo, ContextInfo.accid)
print(f"卖出非目标股: {stock}")
# 5.2 买入/调整目标股票
for stock in target_stocks:
# 目标权重下单,QMT会自动计算需要买卖的数量
order_target_percent(stock, target_weight, ContextInfo, ContextInfo.accid)
print(f"调整 {stock} 仓位至 {target_weight:.2%}")
# -*- coding: gbk -*-:
ContextInfo.get_factor_data:
Valuation_and_Market_Cap.PE(市盈率)作为核心筛选指标。order_target_percent:
调仓逻辑:
current_month 与 last_month 对比。一旦月份发生变化(例如从 1月变到 2月),就会触发一次选股和交易。Q: 为什么回测没有交易记录?
A: 最大的可能是没有下载多因子数据。请去数据管理界面下载。另外,请检查回测时间段内是否包含交易日。
Q: 如何修改为按 PB(市净率)选股?
A: 将代码中排序的那一行:
df.sort_values(by='Valuation_and_Market_Cap.PE', ...)
修改为:
df.sort_values(by='Valuation_and_Market_Cap.PB', ...) 即可。
Q: 实盘可以直接用吗?
A: 实盘需要将 init 函数中的 ContextInfo.accid = 'test' 修改为您真实的资金账号,并将策略运行模式切换为“实盘”或“模拟”。建议先在模拟盘充分测试。