如何实现Q语言通用投资组合平仓策略回测函数
投资组合平仓策略回测的通用实现需求
基础数据说明
现有示例投资组合表 p,存储每日新开仓的带方向交易仓位 signed_qty,表结构构造代码如下:
p:([]date:(2013.07.01+1000#til 200); bb_code:((200#`TSLA),(200#`MSFT),(200#`GOOG),(200#`GS),(200#`AAPL)); fill_px:1000?10e; signed_qty:(1000?(-1, 1)) * 1000?10000);
回测规则
需要针对不同平仓策略,计算每日交易流水与持仓量,规则核心参数定义为:
n:建仓完成后的固定持有天数,这段时间内不做任何平仓操作,仓位保持初始建仓量不变m:固定持有期结束后,用于均匀平完全部初始仓位的交易天数
待回测的典型策略包括:- 持有2天(n=2),后续3天内完成平仓(m=3)
- 持有1天(n=1),后续4天内完成平仓(m=4)
- 自建仓次日起开始平仓,4天内完成全部平仓(n=0, m=4)
可通过调整n、m参数适配任意同类型规则的策略。
现有实现情况
目前已针对 n=3、m=4 的场景编写了逐天硬编码的计算逻辑,代码冗余度高,无法适配任意参数的动态调整,原始实现代码如下:
/ 增加前一行标的代码字段,用于判断是否为同一标的的连续持仓 p:update prev_bb_code: prev bb_code from p; / 建仓后第1天(t+1)不交易,仓位与建仓日保持一致 p:update qty:prev signed_qty from p; p:update signed_qty_p1:qty from p where bb_code = prev_bb_code; p:update traded_qty_p1:(signed_qty_p1 - qty) from p; / 建仓后第2天(t+2)不交易,仓位与前一日保持一致 p:update qty:prev signed_qty_p1 from p; p:update signed_qty_p2:qty from p where bb_code = prev_bb_code; p:update traded_qty_p2:(signed_qty_p2 - qty) from p; / 建仓后第3天(t+3)开始第一次平仓,保留初始仓位的3/4 p:update qty:prev signed_qty_p2 from p; p:update signed_qty_p3:"f"${$[x<0; ceiling((3%4.0)*x); floor((3%4.0)*x)]} each qty from p where bb_code = prev_bb_code; p:update traded_qty_p3:(signed_qty_p3 - qty) from p; / 建仓后第4天(t+4)第二次平仓,保留初始仓位的2/4 p:update qty:prev qty, prev_qty:prev signed_qty_p3 from p; p:update signed_qty_p4:"f"${$[y=0n;0n;$[x<0; max((ceiling((2%4.0)*x)),y); min((floor((2%4.0)*x)),y)]]}'[qty; prev_qty] from p where bb_code=prev_bb_code; p:update traded_qty_p4:(signed_qty_p4 - prev_qty) from p; / 建仓后第5天(t+5)第三次平仓,保留初始仓位的1/4 p:update qty:prev qty, prev_qty:prev signed_qty_p4 from p; p:update signed_qty_p5:"f"${$[y=0n;0n;$[x<0; max((ceiling((1%4.0)*x)),y); min((floor((1%4.0)*x)),y)]]}'[qty; prev_qty] from p where bb_code=prev_bb_code; p:update traded_qty_p5:(signed_qty_p5 - prev_qty) from p; / 建仓后第6天(t+6)完成全部平仓,仓位归0 p:update qty:prev qty, prev_qty:prev signed_qty_p5 from p; p:update signed_qty_p6:"f"${$[y=0n;0n;$[x<0; max((ceiling((0%4.0)*x)),y); min((floor((0%4.0)*x)),y)]]}'[qty; prev_qty] from p where bb_code=prev_bb_code; p:update traded_qty_p6:(signed_qty_p6 - prev_qty) from p; / 聚合每日平仓交易量、计算账户总净持仓 p:update unwind_qty:(0^traded_qty_p1 + 0^traded_qty_p2 + 0^traded_qty_p3 + 0^traded_qty_p4 + 0^traded_qty_p5 + 0^traded_qty_p6) from p; p:update net_position:(0^signed_qty + 0^signed_qty_p1 + 0^signed_qty_p2 + 0^signed_qty_p3 + 0^signed_qty_p4 + 0^signed_qty_p5 + 0^signed_qty_p6) from p; / 保留最终输出的核心字段 p: select date, bb_code, fill_px, signed_qty, unwind_qty, net_position from p;
核心诉求
当前的逐天硬编码实现冗余度极高,无法适配任意n、m参数的动态调整,需要通用性强、逻辑精简的实现方案。
内容的提问来源于stack exchange,提问作者Gerry
相关产品推荐
相关产品推荐

