🚀 AI 一键生成 ptrade 策略代码

PTrade 平台如何开发针对新股上市初期的交易策略?

ptrade | 发布时间: 2025/12/17
以下内容由 EasyQuant 生成。

问题描述

我想写一个交易新股的策略,比如在新股上市第一天如果突破某个价格就买入。

解决方案

这是一个基于PTrade框架的新股上市首日突破策略。

策略逻辑说明

  1. 筛选新股:在每日盘前(before_trading_start),获取全市场股票信息,筛选出上市日期(listed_date)等于当前交易日期的股票。
  2. 设定突破阈值:设定一个突破比例(例如开盘价的5%)。
  3. 盘中监控:在分钟级别的 handle_data 中,监控新股的当前价格。
  4. 触发交易:如果 当前价格 > 开盘价 * (1 + 突破比例),且当前没有持仓,则执行买入操作。

注意事项

  • 回测限制:PTrade回测模式不支持 get_snapshot(快照数据),因此代码中使用 data[security].close 获取当前分钟收盘价来模拟最新价。
  • 实盘差异:如果是实盘,建议使用 tick_data 函数配合 get_snapshot 进行更灵敏的Tick级别监控。下面的代码是基于分钟级别(handle_data)编写的,通用性更强,既可回测也可实盘。
  • 风险提示:新股(特别是注册制新股)上市首日波动极大,且可能没有涨跌幅限制,请务必注意风险控制。

策略代码

import datetime

def initialize(context):
    """
    初始化函数,设置策略参数
    """
    # 设定突破比例,例如 0.05 代表价格超过开盘价 5% 时买入
    g.breakout_ratio = 0.05
    
    # 单只股票买入金额
    g.trade_value = 50000
    
    # 用于存储当日上市的新股列表
    g.today_new_stocks = []
    
    # 开启盘前运行,以便筛选新股
    set_parameters(holiday_not_do_before="0")
    
    log.info("策略初始化完成,突破阈值设定为开盘价的: +{}%".format(g.breakout_ratio * 100))

def before_trading_start(context, data):
    """
    盘前处理:筛选当日上市的新股
    """
    # 重置当日新股列表
    g.today_new_stocks = []
    
    # 获取当前回测/交易日期的字符串格式 YYYY-MM-DD
    current_date_str = context.blotter.current_dt.strftime("%Y-%m-%d")
    
    # 获取当日A股所有代码
    # 注意:全市场扫描在回测中可能较慢,实盘中通常只关注特定列表或通过其他方式获取
    all_stocks = get_Ashares()
    
    # 批量获取股票基础信息(包含上市日期)
    # 为了提高效率,这里演示全市场获取,实际使用建议缩小范围
    stock_infos = get_stock_info(all_stocks)
    
    for stock in all_stocks:
        info = stock_infos.get(stock)
        if info:
            listed_date = info.get('listed_date')
            # 如果上市日期等于今天,加入列表
            if listed_date == current_date_str:
                g.today_new_stocks.append(stock)
    
    if len(g.today_new_stocks) > 0:
        log.info("今日上市新股: {}".format(g.today_new_stocks))
        # 将新股加入股票池,确保handle_data能收到数据
        set_universe(g.today_new_stocks)
    else:
        log.info("今日无新股上市。")
        set_universe([])

def handle_data(context, data):
    """
    盘中处理:监控价格并下单
    """
    # 如果没有新股,直接返回
    if not g.today_new_stocks:
        return

    for stock in g.today_new_stocks:
        # 确保数据存在
        if stock not in data:
            continue
            
        # 获取当前价格和开盘价
        # 在分钟回测中,close为该分钟收盘价;实盘中为最新推送到策略的价格
        current_price = data[stock].close
        open_price = data[stock].open
        
        # 异常数据保护:如果开盘价为0或空,跳过
        if open_price is None or open_price <= 0:
            continue
            
        # 计算目标突破价格
        target_price = open_price * (1 + g.breakout_ratio)
        
        # 获取当前该股票的持仓
        position = get_position(stock)
        
        # 交易逻辑:
        # 1. 当前价格大于目标价格
        # 2. 当前该股票持仓为0(避免重复买入)
        if current_price > target_price and position.amount == 0:
            log.info("股票 {} 触发突破买入!开盘价: {}, 当前价: {}, 目标价: {}".format(
                stock, open_price, current_price, target_price
            ))
            
            # 下单买入指定金额
            # 注意:新股首日可能波动剧烈,市价单可能成交在不可预期的价格
            # 这里使用限价单保护,或者直接用 order_value (通常默认为市价或最新价)
            # 为了演示简单,这里使用 order_value
            order_id = order_value(stock, g.trade_value)
            
            if order_id:
                log.info("已发送买入指令,订单ID: {}".format(order_id))
            else:
                log.warning("下单失败,可能是资金不足或停牌")

def after_trading_end(context, data):
    """
    盘后处理
    """
    if len(g.today_new_stocks) > 0:
        log.info("今日交易结束,监控新股列表: {}".format(g.today_new_stocks))

常见问题 (Q&A)

Q: 为什么回测时没有买入?
A:

  1. 请检查回测时间段内是否有新股上市。
  2. PTrade回测中,如果股票上市首日数据缺失(某些数据源可能不包含首日分钟线),会导致无法触发。
  3. 检查 g.breakout_ratio 是否设置过高,导致价格未达到触发条件。

Q: 如何在实盘中让反应速度更快?
A:
实盘建议使用 tick_data(context, data) 函数替代 handle_datatick_data 每3秒运行一次(取决于行情推送),可以捕捉更细微的价格变动。在 tick_data 中,你可以使用 get_snapshot(stock) 来获取最新的买一卖一价格。

Q: 代码中的 get_Ashares() 会不会太慢?
A:
在回测中,每天调用一次 get_Ashares() 获取全市场几千只股票并检查上市日期可能会有轻微的性能影响。在实盘中,通常你已经知道今天要上市的新股代码,可以直接在 initialize 或通过外部文件读取代码列表,直接 set_universe(['新股代码']),这样效率最高。

Q: 注册制新股(科创板/创业板)首日没有涨跌幅限制,策略需要调整吗?
A:
本策略正是适用于无涨跌幅限制或涨幅限制较宽(如44%)的场景。如果是主板旧规则(首日涨停44%且很难买入),这个策略可能很难成交,因为开盘即秒板。对于注册制新股,价格波动大,突破买入策略更为有效,但也伴随更高风险,建议配合止损逻辑使用。