3 分钟快速生成代码
输入想法,AI 即刻生成可运行代码
在 QMT 平台中,默认的运行机制是行情驱动、逐 K 线运行。在盘中实时交易时,当前最新的一根 K 线(Bar)尚未走完,每一个 Tick 数据的推送都会触发一次 handlebar(ContextInfo) 函数。这会导致在 K 线形成过程中频繁出现“信号闪烁”或“虚假信号”。
本文将为您深度剖析 QMT 的盘中运行机制,并提供实用的代码过滤方案。
handlebar 就会被执行一次。如果您的策略逻辑直接在 handlebar 中判断价格并下单,那么在 K 线没走完时,价格上下波动就会反复触发下单信号。handlebar 时,策略所做的变量更改不会被平台保存,也不会发送真实的交易信号。但如果您开启了 quickTrade=1(立即下单),虚假信号就会被立刻推送至柜台,造成误交易。ContextInfo.is_last_bar() 与默认下单机制(最安全)QMT 默认的 passorder 机制会自动在当前 K 线确定后(最后一个 Tick 判定通过),在下一根 K 线的第一个 Tick 发出信号。如果您不需要盘中抢跑,只需保持默认设置,并使用 is_last_bar() 限制计算范围:
#coding:gbk
def init(ContextInfo):
ContextInfo.set_universe(['600000.SH'])
def handlebar(ContextInfo):
# 仅在最后一根 K 线上进行盘中实时判断
if not ContextInfo.is_last_bar():
return
# 获取最新行情
close_prices = ContextInfo.get_history_data(1, '1d', 'close')
stock = ContextInfo.get_universe()[0]
# 策略逻辑判断
if close_prices[stock][-1] > 10.0:
# quickTrade 默认为 0,代表等待当前 Bar 走完(最后一个 Tick 确定)后,在下一根 Bar 的第一个 Tick 下单
passorder(23, 1101, '您的资金账号', stock, 5, -1, 100, 'MyStrategy', 0, ContextInfo)
ContextInfo.is_new_bar() 锁定新 K 线开始(防止单根 Bar 重复触发)如果您希望在**新一根 K 线刚生成(第一个 Tick 到来)**时只执行一次逻辑,可以使用 is_new_bar() 进行过滤:
#coding:gbk
def init(ContextInfo):
ContextInfo.set_universe(['600000.SH'])
def handlebar(ContextInfo):
# 判定是否为新 K 线的第一个 Tick
if ContextInfo.is_new_bar():
stock = ContextInfo.get_universe()[0]
print(f"新 K 线生成,当前 Bar 索引: {ContextInfo.barpos},开始执行信号判定。")
# 在此处编写只执行一次的逻辑
do_order() 配合如果您运行在日 K 线周期,由于下一个 K 线要等到第二天,默认机制会导致当日无法下单。此时可以使用 do_order(ContextInfo) 函数,在盘中指定时间点,把上一根 K 线确定的有效信号立刻发送出去,避免 Tick 波动干扰:
#coding:gbk
import time
def init(ContextInfo):
ContextInfo.set_account('您的资金账号')
def handlebar(ContextInfo):
# 编写您的基础下单逻辑
order_lots('600000.SH', 1, ContextInfo, '您的资金账号')
# 获取当前最新 Tick 时间
tick_timetag = ContextInfo.get_tick_timetag()
int_time = int(timetag_to_datetime(tick_timetag, '%H%M%S'))
# 在每天上午 10:00:00 到 10:00:05 之间,将上一根 K 线确定的信号立刻发出,且只发一次
if 100000 <= int_time < 100005:
do_order(ContextInfo)
quickTrade=1:该参数会使最后一根 K 线没有走完时也立即下单。除非您有极高频的盘中突破抢跑需求,否则请保持默认值 0。handlebar 的触发频率。