🚀 AI 一键生成 joinquant 策略代码
立即体验
👉 AI 生成代码 👈

JoinQuant策略中一分钟内分多笔下单可以使用time.sleep()吗?

joinquant | 发布时间: 2026/5/29
以下内容由 EasyQuant 生成。

问题描述

关于一创实盘下单的一个疑问

请问我一分钟内想分多笔下单,可以用time.sleep()吗?因为我的策略是按天回测的,不知道可不可以这样。

解决方案

核心解答

不可以,强烈不建议在 JoinQuant(聚宽)的回测或模拟交易中使用 time.sleep() 来实现分笔下单。

特别是在按天回测的策略中,这种做法不仅无法达到你预期的“分时段下单”效果,还可能导致策略运行失败。

为什么不能用 time.sleep()

  1. 逻辑时间 vs 物理时间
    JoinQuant 的回测和模拟交易引擎是基于逻辑时间(即 context.current_dt)驱动的。在按天回测模式下,引擎每天只会在固定的时间点(通常是 09:30:00)调用一次你的交易函数。使用 time.sleep() 只会暂停服务器上 Python 进程的物理时间,但逻辑时间并不会随之流逝。这意味着你 sleep 完之后下的单,在回测引擎看来,依然是在同一个逻辑时间点(09:30:00)下的单。

  2. 超时被杀进程的风险
    根据 JoinQuant API 文档规定,每个函数运行时间不能超过 1800 秒。如果你在策略中大量使用 time.sleep(),很容易导致函数执行超时,系统会强制终止你的策略进程,并抛出 TimeoutError

  3. 撮合机制的限制
    在按天频率下,市价单是按最新价+滑点撮合,限价单是按分钟 Bar 撮合。在同一个逻辑时间点连续下多笔单,引擎会将其视为同一时刻的批量订单,无法模拟出真实市场中“隔几秒下一笔”的盘口冲击效果。

正确的日内分笔下单解决方案

如果你希望在日内(甚至一分钟内)分多笔下单,应该改变策略的时间驱动方式,而不是使用物理休眠。以下是推荐的做法:

方案一:使用多个 run_daily 定时任务(推荐)

如果你只是想在每天的特定几个时间点分别下单,可以在 initialize 函数中注册多个定时任务。引擎会在到达指定的逻辑时间时自动触发这些函数。

def initialize(context):
    # 每天 09:30 执行第一笔
    run_daily(order_part_1, time='09:30')
    # 每天 09:31 执行第二笔
    run_daily(order_part_2, time='09:31')
    # 每天 09:35 执行第三笔
    run_daily(order_part_3, time='09:35')

def order_part_1(context):
    order('000001.XSHE', 100)

def order_part_2(context):
    order('000001.XSHE', 100)

def order_part_3(context):
    order('000001.XSHE', 100)

方案二:将回测频率改为“按分钟”

如果你的分笔逻辑比较复杂(例如根据上一分钟的成交情况决定下一分钟的下单),你需要将策略的运行频率从“天”改为“分钟”。

def initialize(context):
    # 设定为每分钟运行一次
    run_daily(handle_minute, time='every_bar')
    g.order_count = 0

def handle_minute(context):
    # 例如:在 09:30 到 09:35 之间,每分钟下一次单
    if context.current_dt.hour == 9 and 30 <= context.current_dt.minute <= 35:
        if g.order_count < 5:
            order('000001.XSHE', 100)
            g.order_count += 1

方案三:Tick 级别回测(针对极高频)

如果你真的需要在一分钟内(例如每隔几秒)进行精确的下单控制,分钟频率也无法满足,你需要申请开通 Tick 级回测权限,并使用 handle_tick 函数来处理每 3 秒(股票)或 0.5 秒(期货)一次的行情快照。

总结:量化平台的引擎是事件驱动和逻辑时间驱动的,请始终使用平台提供的定时 API(run_daily)或频率设置来控制执行时机,切勿使用 time.sleep()