3 分钟快速生成代码
输入想法,AI 即刻生成可运行代码
要在聚宽(JoinQuant)中实现“每次股票价格变动时都执行一次”的策略,你需要使用 Tick 级频率。
在聚宽的架构中,标准的 handle_data 函数通常用于按天或按分钟运行。要捕捉每一次价格变动(快照),必须使用事件驱动的 handle_tick 函数,并配合 subscribe 订阅功能。
以下是实现该策略的关键步骤和完整代码示例:
initialize 中调用 set_option('use_real_price', True)。subscribe(security, 'tick') 函数订阅你关注的标的。通常在 before_trading_start 或 initialize 中进行。这是一个完整的 Tick 级策略示例。它订阅了平安银行(000001.XSHE),并在每次价格变动时打印当前价格。为了演示交易,代码中包含了一个简单的逻辑:如果当前价大于开盘价则买入,否则卖出。
# -*- coding: utf-8 -*-
import jqdata
def initialize(context):
"""
初始化函数,设定基准等等
"""
# 设定沪深300作为基准
set_benchmark('000300.XSHG')
# 【重要】Tick级回测必须开启动态复权模式(真实价格)
set_option('use_real_price', True)
# 设定要操作的股票,例如平安银行
g.security = '000001.XSHE'
# 设置手续费(可选,这里设置为股票类默认费率)
set_order_cost(OrderCost(close_tax=0.001, open_commission=0.0003, close_commission=0.0003, min_commission=5), type='stock')
# 过滤日志,避免Tick级别日志过多导致卡顿,只显示error级别以上的系统日志
# log.set_level('order', 'error')
def before_trading_start(context):
"""
开盘前运行函数
"""
# 【重要】订阅标的的 tick 事件
# 只有订阅了,handle_tick 才会被触发
subscribe(g.security, 'tick')
log.info(f"已订阅 {g.security} 的Tick数据")
def handle_tick(context, tick):
"""
Tick处理函数
该函数在策略订阅的标的产生 tick 事件时被调用一次。
参数 tick: tick 对象,存放了触发 handle_tick 事件的 tick 数据。
"""
# 获取当前时间
current_time = tick.datetime
# 获取最新价
current_price = tick.current
# 获取当日开盘价
open_price = tick.open
# 打印Tick信息 (注意:Tick级回测日志量巨大,实际策略中建议少打日志)
# log.info(f"时间: {current_time}, 代码: {tick.code}, 最新价: {current_price}")
# --- 简单的交易逻辑示例 ---
# 如果当前价格高于开盘价,且没有持仓,则买入
if current_price > open_price and context.portfolio.positions[tick.code].total_amount == 0:
# 下单买入 100 股
order(tick.code, 100)
log.info(f"Tick触发买入: 价格 {current_price} > 开盘价 {open_price}")
# 如果当前价格低于或等于开盘价,且有持仓,则卖出
elif current_price <= open_price and context.portfolio.positions[tick.code].closeable_amount > 0:
# 卖出所有持仓
order_target(tick.code, 0)
log.info(f"Tick触发卖出: 价格 {current_price} <= 开盘价 {open_price}")
def after_trading_end(context):
"""
收盘后运行函数
"""
# 取消订阅,清理资源
unsubscribe_all()
log.info("收盘,取消所有Tick订阅")
handle_data(分钟/日级回调)通常不会被调用,或者不建议混用,应主要逻辑放在 handle_tick 中。tick 对象包含了丰富的盘口信息,如 tick.a1_v (卖一量), tick.b1_p (买一价) 等,可用于编写更复杂的盘口策略。handle_tick 不会触发。