套利是一种稳定性高,但盈利率较低的交易模式。大多数情况下,套利亏损的原因并不是没有好的套利机会,而是当套利机会出现时没有抓住入场时机,出现瘸腿、价差滑点大等问题。算法交易可以根据套利合约盘口的挂单量和委托价,灵活调整委托量和委托顺序,及时追价或撤单,确保套利成功避免瘸腿,减少滑点损失从而锁定收益。
套利两腿合约的活跃程度不同,流动性较低的合约在成交时伴随着较大的滑点,甚至产生瘸腿,反噬盈利。算法交易可同时监控两腿合约的委托状态,当一腿合约交易不活跃,成交困难时,可迅速调整委托顺序和委托价格,优先委托流动性低的一腿确保其优先成交,再委托流动性高的一腿,降低瘸腿风险。
如下图,根据套利价差图表判断可套利区间,由算法交易精细化管理委托过程,根据两腿合约的活跃度设定委托先后顺序,确保双边成交,控制滑点锁定盈利。

思路解析:
/*
根据套利价差图表计算均线和标准差,以N倍标准差构建可套利区间的上轨和下轨用于做多和做空;
根据套利对两腿的活跃度确定委托先后顺序,确保双边成交,避免瘸腿。
*/
Data
CODA:"m2001"; //第一腿合约A
CODB:"m1909"; //第二腿合约B
Vars
Numeric N; //下单手数
Numeric X; //循环变量
Numeric UDP; //上下轨比例
Numeric SHA; //A平仓参数
Numeric SHB; //B平仓参数
Numeric NEWPA; //A最新价
Numeric NEWPB; //B最新价
Numeric BIDPA; //A买一价
Numeric ASKPA; //A卖一价
Numeric BIDPB; //B买一价
Numeric ASKPB; //B卖一价
Numeric BIDVB; //B买一量
Numeric ASKVB; //B卖一量
Numeric BSVB; //B买一量和
Numeric ASVB; //B卖一量和
Numeric MAA; //A平均值
Numeric MAB; //B平均值
Numeric SDA; //A标准差
Numeric SDB; //B标准差
Numeric UPLA; //A上轨
Numeric UPLB; //B上轨
Numeric DNLA; //A下轨
Numeric DNLB; //B下轨
Numeric TKNA; //A数据区长度
Numeric TKNB; //B数据区长度
Numeric BRPA; //A多头可用持仓
Numeric SRPB; //B空头可用持仓
Numeric OPFLG; //模型处理标志
Numeric BKDFLGA; //A买开处理标志
Numeric SPDFLGA; //A卖平处理标志
Numeric SKDFLGB; //B卖开处理标志
Numeric BPDFLGB; //B买平处理标志
Var_TickData TKDA; //A数据区
Var_TickData TKDB; //B数据区
NumericArray TKPA; //A数据价格
NumericArray TKPB; //B数据价格
Global_Numeric BCFLG; //多头处理标志
Global_Numeric BKIDA; //A买开委托
Global_Numeric SPIDA; //A卖平委托
Global_Numeric BKFLGA; //A买开标志
Global_Numeric SPFLGA; //A卖平标志
Global_Numeric SKIDB; //B卖开委托
Global_Numeric BPIDB; //B买平委托
Global_Numeric SKFLGB; //B卖开标志
Global_Numeric BPFLGB; //B买平标志
Begin
//------------------------处理开启------------------------//
If(CODA.A_IsExchangeOpen() == 1) //如果A是开盘状态
{
If(CODB.A_IsExchangeOpen() == 1) //如果B是开盘状态
{
OPFLG = 1; //开启模型处理
}
}
//------------------------变量赋值------------------------//
If(OPFLG == 1) //变量赋值
{
N = 2; //下单手数
UDP = 1.645; //上下轨比例
NEWPA = CODA.Price("New"); //A最新价
NEWPB = CODB.Price("New"); //B最新价
BIDPA = CODA.Price("Bid1"); //A买一价
ASKPA = CODA.Price("Ask1"); //A卖一价
BIDPB = CODB.Price("Bid1"); //B买一价
ASKPB = CODB.Price("Ask1"); //B卖一价
BIDVB = CODB.Price("BidVol1");//B买一量
ASKVB = CODB.Price("AskVol1");//B卖一量
TKDA = Def_TickData("m2001",1,20);//A数据区
TKDB = Def_TickData("m1909",1,20);//B数据区
BRPA = CODA.F_BuyRemainPosition(); //A多头可用持仓
SRPB = CODB.F_SellRemainPosition(); //B空头可用持仓
If(CODA.A_IsSHCode() == 1) //如果A是上期所合约
{
SHA = Enum_ExitToday; //A平仓参数
}
Else //如果A非上期所合约
{
SHA = Enum_Exit; //A平仓参数
}
If(CODB.A_IsSHCode() == 1) //如果B是上期所合约
{
SHB = Enum_ExitToday; //B平仓参数
}
Else //如果B非上期所合约
{
SHB = Enum_Exit; //B平仓参数
}
If(TKDA.State == 1) //如果A数据区有效
{
TKNA = TKDA.Num; //A数据区长度
For X = 0 To TKNA - 1 //遍历A数据区
{
TKPA[X] = TKDA[X].TickPrice; //A数据价格
}
}
If(TKDB.State == 1) //如果B数据区有效
{
TKNB = TKDB.Num; //B数据区长度
For X = 0 To TKNB - 1 //遍历B数据区
{
TKPB[X] = TKDB[X].TickPrice; //B数据价格
}
For X = TKNB - 3 To TKNB - 1 //遍历B数据区
{
BSVB = BSVB + TKDB[X].BidVol1;//B买一量和
ASVB = ASVB + TKDB[X].AskVol1;//B卖一量和
}
}
MAA = AverageArray(TKPA); //A平均值
MAB = AverageArray(TKPB); //B平均值
SDA = StandardDevArray(TKPA,1); //A标准差
SDB = StandardDevArray(TKPB,1); //B标准差
UPLA = MAA + UDP * SDA;//A上轨
DNLA = MAA - UDP * SDA;//A下轨
UPLB = MAB + UDP * SDB;//B上轨
DNLB = MAB - UDP * SDB;//B下轨
}
//------------------------成交判断------------------------//
If(OPFLG == 1) //成交判断
{
If(BKFLGA == 1) //如果有A买开委托
{
If(F_OrderStatus(BKIDA) == Enum_Filled) //如果A买开委托成交
{
Commentary("【多头开仓:A买开委托成交!】");
BCFLG = 2; //已完成多头开仓
BKFLGA = 0; //A买开标志归0
}
}
If(SKFLGB == 1) //如果有B卖开委托
{
If(F_OrderStatus(SKIDB) == Enum_Filled) //如果B卖开委托成交
{
Commentary("【多头开仓:B卖开委托成交!】");
BKDFLGA = 1; //开启A买开处理
SKFLGB = 0; //B卖开标志归0
}
}
If(SPFLGA == 1) //如果有A卖平委托
{
If(F_OrderStatus(SPIDA) == Enum_Filled) //如果A卖平委托成交
{
Commentary("【多头平仓:A卖平委托成交!】");
BCFLG = 0; //多头处理标志归0
SPFLGA = 0; //A卖平标志归0
}
}
If(BPFLGB == 1) //如果有B买平委托
{
If(F_OrderStatus(BPIDB) == Enum_Filled) //如果B买平委托成交
{
Commentary("【多头平仓:B买平委托成交!】");
SPDFLGA = 1; //开启A卖平处理
BPFLGB = 0; //B买平标志归0
}
}
}
//------------------------套利处理------------------------//
If(OPFLG == 1) //套利处理
{
If(BCFLG == 0) //如果未执行多头开仓
{
If((NEWPA > UPLA && NEWPB > UPLB) || (NEWPA < DNLA && NEWPB < DNLB)) //如果满足多头开仓条件
{
If(BIDVB >= ASKVB / 3 && BSVB < ASVB * 2) //如果满足多头开仓条件
{
Commentary("【多头开仓:满足开仓条件!】");
SKDFLGB = 1; //开启B卖开处理
BCFLG = 1; //已执行多头开仓
}
}
}
Else If(BCFLG == 2) //如果已完成多头开仓
{
If((NEWPA > DNLA && NEWPA < UPLA) && (NEWPB > DNLB && NEWPB < UPLB)) //如果满足多头平仓条件
{
Commentary("【多头平仓:满足平仓条件!】");
BPDFLGB = 1; //开启B买平处理
BCFLG = 3; //已执行多头平仓
}
}
}
//------------------------委托处理------------------------//
If(OPFLG == 1) //委托处理
{
If(BKDFLGA == 1) //如果已开启A买开处理
{
If(BKFLGA == 0) //如果没有A买开委托
{
Commentary("【多头开仓:A买开委托发出!】");
BKIDA = CODA.A_SendOrder(Enum_Buy,Enum_Entry,N,ASKPA); //发出A买开委托
BKFLGA = 1; //已发出A买开委托
}
}
If(SKDFLGB == 1) //如果已开启B卖开处理
{
If(SKFLGB == 0) //如果没有B卖开委托
{
Commentary("【多头开仓:B卖开委托发出!】");
SKIDB = CODB.A_SendOrder(Enum_Sell,Enum_Entry,N,BIDPB); //发出B卖开委托
SKFLGB = 1; //已发出B卖开委托
}
}
If(SPDFLGA == 1) //如果已开启A卖平处理
{
If(BRPA > 0) //如果有A多头可用持仓
{
Commentary("【多头平仓:A卖平委托发出!】");
SPIDA = CODA.A_SendOrder(Enum_Sell,SHA,BRPA,BIDPA); //发出A卖平委托
SPFLGA = 1; //已发出A卖平委托
}
}
If(BPDFLGB == 1) //如果已开启B买平处理
{
If(SRPB > 0) //如果有B空头可用持仓
{
Commentary("【多头平仓:B买平委托发出!】");
BPIDB = CODB.A_SendOrder(Enum_Buy,SHB,SRPB,ASKPB); //发出B买平委托
BPFLGB = 1; //已发出B买平委托
}
}
}
End
编写规则:
(1)套利合约不支持基于Tick图数据的策略;
(2)以价差K线图为基础的趋势套利策略,不支持使用含有资金管理思路的函数,如:Money、LastOffSetProfit、SetDealPercent函数等。
很多交易者在套利交易过程中,往往更重视入场策略,通过设定不同的委托方式保证交易成功,但是任何一种委托方式,都有可能面临交易过程中价差偏移的风险,那么如何规避这种风险呢?我们不妨尝试制定一套退场策略。
在套利分批下单过程中,一旦价差偏离超过可承受滑点范围后,马上终止交易、暂停后续批次委托,并且根据实际情况,处理单边持仓:当单边持仓亏损时,马上进行平仓止损,降低瘸腿风险。当单边持仓盈利时,则对另一腿合约进行追价委托,尽快配成套利对,用单边的盈利弥补价差偏离的成本。如下图,策略运行时前台显示信号点位,由算法在后台自动执行精细化的下单方案。

/*
设定价差偏离可承受范围
当价差偏离超过此范围,立即终止交易,暂停委托,并对当前的持仓进行退场处理:
单边持仓亏损,立即平仓止损;
单边持仓盈利,对另一腿合约配对;
*/
Data
CODA:"m2001"; //第一腿合约A
CODB:"m1909"; //第二腿合约B
Vars
Numeric N; //下单手数
Numeric T; //时间间隔
Numeric PLM; //偏离价位倍数
Numeric SHA; //A平仓参数
Numeric SHB; //B平仓参数
Numeric KCP; //开仓条件价差
Numeric PCP; //平仓条件价差
Numeric NOW; //当前时间
Numeric NPC; //最新价差
Numeric NEWPA; //A最新价
Numeric NEWPB; //B最新价
Numeric BIDPA; //A买一价
Numeric ASKPA; //A卖一价
Numeric BIDPB; //B买一价
Numeric ASKPB; //B卖一价
Numeric ASKVA; //A卖一量
Numeric BIDVB; //B买一量
Numeric MINPA; //A最小变动价位
Numeric BPLA; //A多头持仓盈亏
Numeric SPLB; //B空头持仓盈亏
Numeric BRPA; //A多头可用持仓
Numeric SRPB; //B空头可用持仓
Numeric OPFLG; //模型处理标志
Numeric BKDFLGA; //A买开处理标志
Numeric SPDFLGA; //A卖平处理标志
Numeric SKDFLGB; //B卖开处理标志
Numeric BPDFLGB; //B买平处理标志
Global_Numeric NPCA; //记录价差
Global_Numeric BCFLG; //多头处理标志
Global_Numeric CDFLG; //撤单处理标志
Global_Numeric BKIDA; //A买开委托
Global_Numeric SPIDA; //A卖平委托
Global_Numeric BKFLGA; //A买开标志
Global_Numeric SPFLGA; //A卖平标志
Global_Numeric BKDELA; //A买开撤单标志
Global_Numeric BKSMA; //A买开委托总手数
Global_Numeric BKMA; //A买开委托手数
Global_Numeric SPMA; //A卖平委托手数
Global_Numeric BKTA; //A买开委托时间
Global_Numeric SKIDB; //B卖开委托
Global_Numeric BPIDB; //B买平委托
Global_Numeric SKFLGB; //B卖开标志
Global_Numeric BPFLGB; //B买平标志
Global_Numeric SKDELB; //B卖开撤单标志
Global_Numeric SKSMB; //B卖开委托总手数
Global_Numeric SKMB; //B卖开委托手数
Global_Numeric BPMB; //B买平委托手数
Global_Numeric SKTB; //B卖开委托时间
Begin
//------------------------处理开启------------------------//
If(CODA.A_IsExchangeOpen() == 1) //如果A是开盘状态
{
If(CODB.A_IsExchangeOpen() == 1) //如果B是开盘状态
{
OPFLG = 1; //开启模型处理
}
}
//------------------------变量赋值------------------------//
If(OPFLG == 1) //变量赋值
{
N = 20; //下单手数
T = 5; //时间间隔
PLM = 3; //偏离价位倍数
KCP = 5; //开仓条件价差
PCP = 10; //平仓条件价差
NOW = CurrentTime(); //当前时间
NEWPA = CODA.Price("New"); //A最新价
NEWPB = CODB.Price("New"); //B最新价
BIDPA = CODA.Price("Bid1"); //A买一价
ASKPA = CODA.Price("Ask1"); //A卖一价
BIDPB = CODB.Price("Bid1"); //B买一价
ASKPB = CODB.Price("Ask1"); //B卖一价
ASKVA = CODA.Price("AskVol1"); //A卖一量
BIDVB = CODB.Price("BidVol1"); //B买一量
MINPA = CODA.Price("MinPrice"); //A最小变动价位
NPC = NEWPA - NEWPB; //最新价差
BPLA = CODA.F_BuyProfitLoss(); //A多头持仓盈亏
SPLB = CODB.F_SellProfitLoss(); //B空头持仓盈亏
BRPA = CODA.F_BuyRemainPosition(); //A多头可用持仓
SRPB = CODB.F_SellRemainPosition(); //B空头可用持仓
If(CODA.A_IsSHCode() == 1) //如果A是上期所合约
{
SHA = Enum_ExitToday; //A平仓参数
}
Else //如果A非上期所合约
{
SHA = Enum_Exit; //A平仓参数
}
If(CODB.A_IsSHCode() == 1) //如果B是上期所合约
{
SHB = Enum_ExitToday; //B平仓参数
}
Else //如果B非上期所合约
{
SHB = Enum_Exit; //B平仓参数
}
}
//------------------------成交判断------------------------//
If(OPFLG == 1) //成交判断
{
If(BKFLGA == 1) //如果有A买开委托
{
If(F_OrderStatus(BKIDA) == Enum_Filled) //如果A买开委托成交
{
Commentary("【多头开仓:A买开委托成交!】");
If(BKDELA == 0 || BKDELA == 1) //如果非撤单处理撤单
{
If(BKSMA > 0) //如果有剩余A买开委托手数
{
BKDFLGA = 1; //开启A买开处理
}
}
Else If(BKDELA == 2) //如果是撤单处理撤单
{
BPDFLGB = 2; //开启B买平处理
}
BKFLGA = 0; //A买开标志归0
BKDELA = 0; //A买开撤单标志归0
}
Else If(F_OrderStatus(BKIDA) == Enum_Canceled) //如果A买开委托已撤
{
Commentary("【多头开仓:A买开委托已撤!】");
If(BKDELA == 1) //如果是追价处理撤单
{
If(F_OrderFilledLot(BKIDA) > 0) //如果A买开委托部分成交
{
BKMA = BKMA - F_OrderFilledLot(BKIDA); //A买开委托手数
}
If(BKMA > 0) //如果A买开委托手数大于0
{
Commentary("【多头开仓:A买开委托追价!】");
BKIDA = CODA.A_SendOrder(Enum_Buy,Enum_Entry,BKMA,ASKPA); //发出A买开委托
BKTA = NOW; //A买开委托时间
}
}
Else If(BKDELA == 2) //如果是撤单处理撤单
{
BPDFLGB = 2; //开启B买平处理
BKFLGA = 0; //A买开标志归0
}
BKDELA = 0; //A买开撤单标志归0
}
Else If(F_OrderStatus(BKIDA) == Enum_Declared || F_OrderStatus(BKIDA) == Enum_FillPart) //如果A买开委托挂单
{
If(BKDELA == 0) //如果未撤单
{
If(CDFLG == 1 && TimeDiff(BKTA,NOW) >= T) //如果已开启追价处理,且时间间隔T秒
{
Commentary("【多头开仓:A买开委托撤单!】");
CODA.F_DeleteOrder(F_OrderContractNo(BKIDA)); //撤掉A买开委托挂单
BKDELA = 1; //已发出撤掉A买开委托挂单
}
Else If(CDFLG == 2) //如果已开启撤单处理
{
Commentary("【多头开仓:A买开委托撤单!】");
CODA.F_DeleteOrder(F_OrderContractNo(BKIDA)); //撤掉A买开委托挂单
BKDELA = 2; //已发出撤掉A买开委托挂单
}
}
}
}
If(SKFLGB == 1) //如果有B卖开委托
{
If(F_OrderStatus(SKIDB) == Enum_Filled) //如果B卖开委托成交
{
Commentary("【多头开仓:B卖开委托成交!】");
If(SKDELB == 0 || SKDELB == 1) //如果非撤单处理撤单
{
If(SKSMB > 0) //如果有剩余B卖开委托手数
{
SKDFLGB = 1; //开启B卖开处理
}
}
Else If(SKDELB == 2) //如果是撤单处理撤单
{
SPDFLGA = 2; //开启A卖平处理
}
SKFLGB = 0; //B卖开标志归0
SKDELB = 0; //B卖开撤单标志归0
}
Else If(F_OrderStatus(SKIDB) == Enum_Canceled) //如果B卖开委托已撤
{
Commentary("【多头开仓:B卖开委托已撤!】");
If(SKDELB == 1) //如果是追价处理撤单
{
If(F_OrderFilledLot(SKIDB) > 0) //如果B卖开委托部分成交
{
SKMB = SKMB - F_OrderFilledLot(SKIDB); //B卖开委托手数
}
If(SKMB > 0) //如果B卖开委托手数大于0
{
Commentary("【多头开仓:B卖开委托追价!】");
SKIDB = CODB.A_SendOrder(Enum_Sell,Enum_Entry,SKMB,BIDPB); //发出B卖开委托
SKTB = NOW; //B卖开委托时间
}
}
Else If(SKDELB == 2) //如果是撤单处理撤单
{
SPDFLGA = 2; //开启A卖平处理
SKFLGB = 0; //B卖开标志归0
}
SKDELB = 0; //B卖开撤单标志归0
}
Else If(F_OrderStatus(SKIDB) == Enum_Declared || F_OrderStatus(SKIDB) == Enum_FillPart) //如果B卖开委托挂单
{
If(SKDELB == 0) //如果未撤单
{
If(CDFLG == 1 && TimeDiff(SKTB,NOW) >= T) //如果已开启追价处理,且时间间隔T秒
{
Commentary("【多头开仓:B卖开委托撤单!】");
CODB.F_DeleteOrder(F_OrderContractNo(SKIDB)); //撤掉B卖开委托挂单
SKDELB = 1; //已发出撤掉B卖开委托挂单
}
Else If(CDFLG == 2) //如果已开启撤单处理
{
Commentary("【多头开仓:B卖开委托撤单!】");
CODB.F_DeleteOrder(F_OrderContractNo(SKIDB)); //撤掉B卖开委托挂单
SKDELB = 2; //已发出撤掉B卖开委托挂单
}
}
}
}
If(SPFLGA == 1) //如果有A卖平委托
{
If(F_OrderStatus(SPIDA) == Enum_Filled) //如果A卖平委托成交
{
Commentary("【多头平仓:A卖平委托成交!】");
SPFLGA = 0; //A卖平标志归0
}
}
If(BPFLGB == 1) //如果有B买平委托
{
If(F_OrderStatus(BPIDB) == Enum_Filled) //如果B买平委托成交
{
Commentary("【多头平仓:B买平委托成交!】");
BPFLGB = 0; //B买平标志归0
}
}
}
//------------------------套利处理------------------------//
If(OPFLG == 1) //套利处理
{
If(BCFLG == 0) //如果未执行多头开仓
{
If(NPC <= KCP) //如果满足多头开仓条件
{
Commentary("【多头开仓:满足开仓条件!】");
NPCA = NPC; //记录价差
BKSMA = N; //A买开委托总手数
SKSMB = N; //B卖开委托总手数
BKDFLGA = 1; //开启A买开处理
SKDFLGB = 1; //开启B卖开处理
CDFLG = 0; //撤单处理标志归0
BCFLG = 1; //已执行多头开仓
}
}
Else If(BCFLG == 1) //如果已执行多头开仓
{
If((BKFLGA == 0 && BKSMA == 0) && (SKFLGB == 0 && SKSMB == 0)) //如果已完成多头开仓
{
Commentary("【多头开仓:多头开仓完成!】");
BCFLG = 2; //已完成多头开仓
}
Else If(BKFLGA == 0 && BKSMA == 0) //如果A已完成多头开仓
{
If(Abs(NPC - NPCA) > PLM * MINPA) //如果价差偏离过大
{
If(BPLA > 0) //如果A多头持仓盈利
{
CDFLG = 1; //开启追价处理
}
Else If(BPLA < 0) //如果A多头持仓亏损
{
CDFLG = 2; //开启撤单处理
}
}
}
Else If(SKFLGB == 0 && SKSMB == 0) //如果B已完成多头开仓
{
If(Abs(NPC - NPCA) > PLM * MINPA) //如果价差偏离过大
{
If(SPLB > 0) //如果B空头持仓盈利
{
CDFLG = 1; //开启追价处理
}
Else If(SPLB < 0) //如果B空头持仓亏损
{
CDFLG = 2; //开启撤单处理
}
}
}
}
If(BCFLG == 2) //如果已完成多头开仓
{
If(NPC >= PCP) //如果满足多头平仓条件
{
Commentary("【多头平仓:满足平仓条件!】");
SPDFLGA = 1; //开启A卖平处理
BPDFLGB = 1; //开启B买平处理
BCFLG = 3; //已执行多头平仓
}
}
}
//------------------------委托处理------------------------//
If(OPFLG == 1) //委托处理
{
If(BKDFLGA == 1) //如果已开启A买开处理
{
If(BKFLGA == 0) //如果没有A买开委托
{
BKMA = Max(Min(BKSMA,ASKVA),1); //A买开委托手数
BKSMA = BKSMA - BKMA; //A买开委托总手数
Commentary("【委托手数:" + Text(BKMA) + "手!】");
Commentary("【剩余手数:" + Text(BKSMA) + "手!】");
Commentary("【多头开仓:A买开委托发出!】");
BKIDA = CODA.A_SendOrder(Enum_Buy,Enum_Entry,BKMA,ASKPA); //发出A买开委托
BKTA = NOW; //A买开委托时间
BKFLGA = 1; //已发出A买开委托
}
}
If(SKDFLGB == 1) //如果已开启B卖开处理
{
If(SKFLGB == 0) //如果没有B卖开委托
{
SKMB = Max(Min(SKSMB,BIDVB),1); //B卖开委托手数
SKSMB = SKSMB - SKMB; //B卖开委托总手数
Commentary("【委托手数:" + Text(SKMB) + "手!】");
Commentary("【剩余手数:" + Text(SKSMB) + "手!】");
Commentary("【多头开仓:B卖开委托发出!】");
SKIDB = CODB.A_SendOrder(Enum_Sell,Enum_Entry,SKMB,BIDPB); //发出B卖开委托
SKTB = NOW; //B卖开委托时间
SKFLGB = 1; //已发出B卖开委托
}
}
If(SPDFLGA > 0) //如果已开启A卖平处理
{
If(SPFLGA == 0) //如果没有A卖平委托
{
If(BRPA > 0) //如果有A多头可用持仓
{
If(SPDFLGA == 1) //如果是多头平仓卖平
{
SPMA = BRPA; //A卖平委托手数
}
Else If(SPDFLGA == 2) //如果是单腿平仓卖平
{
SPMA = BRPA - SRPB; //A卖平委托手数
}
If(SPMA > 0) //如果A卖平委托手数大于0
{
Commentary("【多头平仓:A卖平委托发出!】");
SPIDA = CODA.A_SendOrder(Enum_Sell,SHA,SPMA,BIDPA); //发出A卖平委托
SPFLGA = 1; //已发出A卖平委托
}
}
}
}
If(BPDFLGB > 0) //如果已开启B买平处理
{
If(BPFLGB == 0) //如果没有B买平委托
{
If(SRPB > 0) //如果有B空头可用持仓
{
If(BPDFLGB == 1) //如果是多头平仓买平
{
BPMB = SRPB; //B买平委托手数
}
Else If(BPDFLGB == 2) //如果是单腿平仓买平
{
BPMB = SRPB - BRPA; //B买平委托手数
}
If(BPMB > 0) //如果B买平委托手数大于0
{
Commentary("【多头平仓:B买平委托发出!】");
BPIDB = CODB.A_SendOrder(Enum_Buy,SHB,BPMB,ASKPB); //发出B买平委托
BPFLGB = 1; //已发出B买平委托
}
}
}
}
}
End