问题描述
解决方案
在 QMT 平台中进行一篮子股票(组合)交易,主要通过 passorder 函数实现。要实现按“固定份数”、“总金额”或“账户资金比例”下单,关键在于设置 orderType(下单方式) 和 volume(下单数量) 这两个参数。
核心参数说明
在使用 passorder 进行组合交易时,opType 通常设置为 25 (组合买入) 或 26 (组合卖出)。orderCode 需要填写你在 QMT 界面中创建好的篮子名称(而非单个股票代码)。
针对您的需求,orderType 的设置如下(以单账号为例):
- 按固定份数下单:
orderType = 2101- 含义:按组合股票数量(篮子中设定的股数)下单。
volume单位:份(即买入 N 倍篮子定义的数量)。
- 按总金额下单:
orderType = 2102- 含义:按组合股票权重分配资金下单。
volume单位:元(即总共花费多少金额,系统根据篮子权重自动分配给各成分股)。
- 按账户资金比例下单:
orderType = 2103- 含义:按账号可用资金的比例下单。
volume单位:比例(范围 0.0 ~ 1.0,例如 0.5 代表 50%)。
策略代码示例
以下代码展示了如何在 QMT 中实现这三种下单方式。
# -*- coding: gbk -*-
def init(ContextInfo):
# 1. 设置资金账号 (请替换为真实的资金账号)
ContextInfo.accid = '6000000000'
ContextInfo.set_account(ContextInfo.accid)
# 2. 定义篮子名称 (前提:需在QMT界面的【策略交易】-【组合交易】中预先创建好该篮子)
ContextInfo.basket_name = 'MySuperBasket'
def handlebar(ContextInfo):
# 获取当前K线位置,避免历史回测重复下单,仅在最后一根K线运行
if not ContextInfo.is_last_bar():
return
# ==============================================================================
# 场景一:按固定份数下单 (orderType = 2101)
# ==============================================================================
# 假设篮子定义里包含 A股 100股,B股 200股。
# 下单 2 份,则实际买入 A股 200股,B股 400股。
# opType=25(组合买入), orderType=2101(按数量), price=-1(市价/默认), volume=2(份)
passorder(25, 2101, ContextInfo.accid, ContextInfo.basket_name, 14, -1, 2, ContextInfo)
print("已执行:按固定份数下单,买入 2 份")
# ==============================================================================
# 场景二:按总金额下单 (orderType = 2102)
# ==============================================================================
# 系统会根据篮子中各股票设定的权重,将 100,000 元分配到各股票进行买入。
# opType=25(组合买入), orderType=2102(按金额), price=-1, volume=100000(元)
passorder(25, 2102, ContextInfo.accid, ContextInfo.basket_name, 14, -1, 100000, ContextInfo)
print("已执行:按总金额下单,买入 100,000 元")
# ==============================================================================
# 场景三:按账户资金比例下单 (orderType = 2103)
# ==============================================================================
# 使用当前账户可用资金的 30% 进行买入,资金分配依据篮子权重。
# opType=25(组合买入), orderType=2103(按比例), price=-1, volume=0.3(30%)
passorder(25, 2103, ContextInfo.accid, ContextInfo.basket_name, 14, -1, 0.3, ContextInfo)
print("已执行:按资金比例下单,使用 30% 可用资金")
注意事项
- 篮子创建:代码中的
orderCode(示例中的'MySuperBasket')必须与 QMT 客户端左侧【策略交易】面板或【模型管理】中创建的组合/篮子名称完全一致。 - 权重设置:
- 使用
2102(按金额)和2103(按比例)时,系统依赖于篮子设置中的权重。如果篮子中没有设置权重,系统通常会按相等权重分配。
- 使用
- 报价类型 (
prType):- 示例中使用了
14(对手价)。 - 对于组合交易,
prType只对篮子逻辑起作用,具体到底层个股下单时,通常建议使用市价或对手价以保证成交率。
- 示例中使用了
- 账号组交易:
- 如果需要对账号组(多个账号)进行一篮子交易,请将
orderType修改为对应的组代码:2201:账号组 - 按数量2202:账号组 - 按权重金额2203:账号组 - 按可用比例
- 如果需要对账号组(多个账号)进行一篮子交易,请将
Q&A
Q: 如果我想卖出一篮子股票,代码怎么改?
A: 将 passorder 的第一个参数 opType 从 25 改为 26 即可。例如 passorder(26, 2101, ...) 表示按份数卖出组合。
Q: 2102 按金额下单时,如果某只股票算出来的股数不足 100 股怎么办?
A: QMT 底层会自动处理。通常会向下取整到 100 的整数倍(即 1 手)。如果分配的金额不足以买入 1 手,该股票可能不会下单。
Q: 可以在代码里动态创建篮子吗?
A: QMT 的 Python API 主要用于调用已存在的篮子进行交易。虽然可以通过文件读写修改本地的篮子配置文件,但标准的做法是在界面上手动创建或导入篮子,然后在代码中引用篮子名称。如果需要完全动态的一篮子交易(例如每分钟成分股都在变),建议使用循环遍历股票列表,对每只股票单独调用 passorder(单股下单模式),而不是使用组合下单接口。