SPL 量化工作台使用教程
前言 —— 量化投资,你也可以
一提起量化投资,普通股民脑海里就会泛起困难的编程语言、繁杂的高频交易、高额的资金门槛,自然会觉得和自己无关。
SPL 量化工作台是北京润乾公司基于开源 SPL 技术实现的一套量化策略设计和回测平台。它让你轻松迈入量化投资的世界——无需编程基础,有 Excel 技能就可以设计策略;无需复杂设备,打开网页就能使用;更无需巨额资金,策略信号人工执行即可。
SPL 量化工作台专为普通投资者设计,具有三大特点:
零编程门槛
告别 Python、C++ 等复杂语言,只需有 Excel 技能就能构建策略。系统将您的公式自动转化为可执行的量化策略,让您专注于投资逻辑而非代码实现。一站式数据服务
每日自动更新 A 股全市场数据,内置近百个常用技术指标(如 MACD、RSI、布林带等),封装复杂的数学运算,您只需 "拿来即用",省去数据收集和处理的烦恼。日 K 线离线策略
专注于基于日 K 线的中低频策略设计,工作台生成信号,再由人工操作,既避免了高昂的自动化交易系统接入成本,又规避了高频交易的技术门槛和资金压力。
在这个工作台上,量化策略的创建和验证变得前所未有的简单:
实时回测:策略修改后立即看到历史表现
可视化分析:清晰直观的收益曲线和风险指标
策略优化:快速调整参数寻找更优组合
现在,量化投资不再是专业人员和机构的专属。无论您是:
想系统验证自己投资理念的散户
希望将经验转化为稳定策略的老股民
对量化感兴趣但缺乏技术背景的投资者
这个工作台都能帮助您以最低的成本,体验专业量化投资的魅力。
量化投资,你也可以!立即访问我们的工作台,开启您的智能投资新时代。
工作台网址:http://stock.raqsoft.com.cn:8092/model.jsp
因股票信息量大,请在大屏幕电脑上使用浏览器操作,不合适小屏幕手机体验。
社区网址:https://c.raqsoft.com.cn/tag/QuantitativeTrading
有疑问可到社区发贴(微信扫码注册),特别是有需要的新指标或做不出来的策略,都可以提出来,我们会再继续完善补充。
掌握这些基本能力后,还可以在SPL 量化编程课进一步学习 SPL 编程以实现更复杂的策略。
1 数据
打开网页,在左上角股票代码框中输入股票代码,比如输入‘600690’查看海尔智家,下方即可显示出海尔智家的日 K 线数据。日 K 线数据的列可以在左边进行勾选,只显示需要用到的列。
在这里可以切换复权类型。需要强调的是:这里的复权计算是按起止日期开始计算,而不是从股票上市日和今天开始计算的。比如现在看到的数据是从 2021-1-1 到 2021-12-31 期间的,选择前复权时,最末尾日期,即 2021-12-31 将用不复权价,前面的价格会做复权。反之 ,后复权则是起头日期,即 2021-1-4 用不复权价,后面的价格做复权。这样的好处是让显示出来价格最接近实际交易价,当然对于策略设计是没有影响的。
在开始和结束输入框中选择起止日期,可以对数据的区间进行过滤,后续的指标计算、策略回测、统计图表的生成都基于这个时间区间进行。
右边提前读数和显示选项,现在不必理会,后续讲到策略时会解释。
还可以用图形的方式观察数据,在左轴、右轴下拉框中选择统计图的 Y 轴,然后用画图,即可显示成图形来查看。
左轴和右轴也可以分别选择多列,这样会生成多条线型图,方便对照:
2 最简单的固定价策略
我们来尝试做一个固定价格买卖策略,策略内容是这样的:如果当日股票的最低价低于 23 元,就买入;反之如果股票的最高价高于 25 元,就全部卖出。然后循环进行这个步骤,看下能否赚钱。
这里我们假设,每次的买入价格为都为 23 元,卖出价格都为 25 元,每次买入数量为 1 手(100 股)。
首先定义买入价格列,第一步:在指标类型下拉框中选择SPL 公式,然后输出列类型选择买卖价格,输出列名选择买价,表达式里输入23,最后点提交。
此时可以看到数据显示框中多出了买价这列:
同时在买入价格下拉框中也多出了买价选项,选择买价作为买入价格:
接着定义卖出价格列,第一步先重新点选一下指标类型下拉框,重新选择SPL 公式(特别强调:即使当前已经是 SPL 公式了,也需要下拉点选一下,表示新建指标,否则会修改原指标),重新点选后会发现页面刷新了:
此时再选择输出列类型为买卖价格,输出列名为卖价,表达式为25.5,点提交:
最后在卖出价格下拉框中选择卖价作为卖出价格:
买入股数和买入金额是互斥的,是指一次买入交易的股数或金额。A 股市场以“手”为单位(1 手 =100 股),买入时通常需为 100 股或其整数倍(如 100 股、200 股等)。科创板(688 开头)和创业板(300 开头)最低 200 股起,可按 1 股递增。
我们这里以 600690 为例,买入股数填100,持续买入打勾,最后点提交:
这时候会弹出对话框:
点确定即可,因为固定价格买卖不需要买卖信号列,直接满足价格即可买卖。最后界面左侧数据显示框会出现交易明细,右侧的回测结果显示统计值,回测结果旁边显示回测时间:
持仓 / 买入 / 卖出这三列显示的数字,表示当前持仓 / 买入 / 卖出的笔数,每一笔的股数和金额取决于前面定义的买入股数 / 买入金额。
鼠标放到持仓 / 买入 / 卖出的数字上,会显示当前持仓或交易明细,其中股数是指这一笔交易的买入股数,买日 / 卖日是指这一笔交易的买入日期 / 卖出日期,如果这一笔股票买入后在回测区间里一直没有卖出,则卖日会显示为空。买价 / 卖价表示这笔股票的买入价格 / 卖出价格,同样的,如果没有卖掉,卖价也显示为空。买额 = 股数 * 买价 + 手续费,卖额 = 股数 * 卖价 - 手续费,这里的意思其实是,买额相当于进行这一笔交易需要花费的总金额,卖额相当于进行这一笔交易后能获得的现金额。
此时点击下一交易行 / 上一交易行按钮,数据会自动滚动到下一个 / 上一个有交易的行,并高亮显示。
这里可以看到,持仓明细里显示的卖日 / 卖价 / 卖额为空,表示当前买入的股票在回测区间没有卖掉。
界面右侧的回测结果用到了一些指标,解释如下:
占用资金:在给定时间段内完成所有交易需要投入的现金综合(包括手续费)。比如某个策略一周内的买卖资金如下表。不难算出,要完成这些交易,需要投入 800 元,那么该策略的占用资金就是 800 元。
买入资金 |
500 |
卖出资金 |
700 |
买入资金 |
1000 |
卖出资金 |
900 |
现金收益:指买卖股票所获得的价差收益,只计算已卖出的股票。例如,8 块买入,买入 100 股,买入手续费 5 元;15 元卖出,卖出手续费 5 元,那么现金收益就是 15*100-5-8*100-5=690。
持仓价值:当前持有的股票价值。例如持有 A 股票 100 股,当前股价 10 元,那么 A 股票的持仓价值就是 1000。
持仓收益:当前的持仓价值 - 持仓成本。
收益率:指收益总额与投资额的比例。收益总额包括现金收益和持仓收益。投资额就是该股票的占用资金。
买盘数:指希望购买的订单数。
赢利数:策略在给定时间段内交易次数中盈利的次数。
亏损数:策略在给定时间段内交易次数中亏损的次数。
买入资金:给定时间段内策略的总买入资金。
卖出资金:给定时间段内策略的总买入资金。
比如某个策略一周内的买卖资金如下表,那么一周内该策略的买入资金就是 1500 元,卖出资金是 1600 元。
买入资金 |
500 |
卖出资金 |
700 |
买入资金 |
1000 |
卖出资金 |
900 |
日波动率:指策略收益率在一定时间内的变动幅度,它反映了市场的不确定性和风险。波动率越高,收益率的波动越剧烈,资产收益率的不确定性就越强;波动率越低,收益率的波动越平缓,资产收益率的确定性就越强。波动率等于每日收益率的标准差。
最大回撤率:描述策略在回测期可能出现的最大亏损幅度,反映了策略的风险承受能力。最大回撤率越小,说明策略的稳定性越高,风险越低。最大回撤率等于最高收益率与之后最低收益的差值与最高收益率 +1 的比值。
年化收益率:(收益率 +1)^(251/ 交易天数)-1。其中“^”是幂指数符号,251 是假定每年交易天数是固定的 251,有时也用 252,交易天数是策略开始到结束的间隔交易天数。
年化波动率:日波动率 *(251/ 交易天数的平方根)。
夏普率:年化收益率 - 无风险收益率后与年化波动率的比值,用来衡量策略的收益风险比。
手续费的算法不同券商可能会不同,这里采用如下公式计算:
买入手续费 =max(交易金额 *0.03%,5)+ 交易金额 *0.001%
卖出手续费:max(买入金额 *0.03%,5)+ 买入金额 *(0.001%+0.05%)
前面定义策略时,勾选了持续买入,表示回测时只要信号列返回 1,第二天就执行买入操作;如果不勾选,则只要当前持仓笔数大于 0,即使信号列返回 1,第二天也不会操作。我们可以把上面的策略按持续买入和不持续买入做个对比:
从上面两图可以看出,如果持续买入打勾,则只要满足买入条件,就会持续买入;反之,只要持仓不为 0,即使满足买入条件,也不会再次买入。
3 双均线策略——SPL 公式
我们再来用这个工作台实现业界常见的双均线策略。
双均线策略基于这样一种假设:观察长期均线(如 10 日均线), 和短期均线(如 5 日均线)。股票价格的动量会朝着短期均线的方向移动。当短期均线穿过长期均线,并超过长期移动平均线时,动量将向上,此时股价可能会上涨,判断为买入。反之,如果短期均线的移动方向相反,股价则可能下跌,判断为卖出。
这时候,对于回测时间区间的第一天来说,判断是否买入卖出要用前面 10 个交易日的数据来计算,因此需要往前读 10 天的数,这就用到了提前读数的功能:
提前读的这 10 天数据可以显示也可以不显示,由显示勾选框来决定。
此策略用到的长期均线和短期均线都需要先定义成指标,方便后面的表达式使用,所以我们第一步先定义这两个指标:
选择SPL 公式,输出列类型为普通,输出列名为MA5(表示为 5 日均线),表达式为收盘 [-4:0].avg():
这句代码中出现了中括号的语法,[a:b]的形式表示取区间值,如,收盘 [-4:0]表示取区间收盘价,从往前数第 4 天开始取,一直取到当前行(0 表示当前行),即共计取到 5 天的收盘价,再用avg()函数求平均值就是 5 日 MA;同理,收盘 [-9:0].avg()就是计算 10 日均价:
10 日均价的输出列名定义为 MA10。好了,有了这两个均价指标列,可以先以图形的方式观察一下:
从图上可以看到一些很明显的上穿下穿交叉点。
下一步就定义买卖信号列:
买卖信号列的输出规则是这样:1 表示第二天执行买入;-1 表示第二天执行卖出;0 表示不操作。需要再次说明的是,这里设计的离线策略,也就是用截止昨日的收盘数据算出的买卖信号列值,来决定第二天的买卖操作。
第一步:选择SPL 公式,输出列类型选择买卖信号,输出列名 MA5_10_Signal,表达式 if(MA5>MA10 && MA5[-1]<=MA10[-1]:1,MA5<MA10 && MA5[-1]>=MA10[-1]:-1;0),最后点提交:
数据显示框中可以看到 MA5_10_Signal 的值:
说明:if(MA5>MA10 && MA5[-1]<=MA10[-1]:1,MA5<MA10 && MA5[-1]>=MA10[-1]:-1;0)表达式的含义:当MA5>MA10 && MA5[-1]<=MA10[-1]满足时返回1,当MA5<MA10 && MA5[-1]>=MA10[-1]满足时返回-1,否则返回0,类似于 Excel 中的表达式:ifs(MA5>MA10 && MA5[-1]<=MA10[-1],1,MA5<MA10 && MA5[-1]>=MA10[-1],-1,0)
有了信号列,我们再用统计图来对比看一下 MA5,MA10, MA5_10_Signal,这里就用到右轴了:
可以看出 MA5_10_Signal 取值为 1 或 -1 的日期,正好是 MA5 和 MA10 交叉后的第一天。
第二步定义策略:买入 / 卖出信号列均下拉选择MA5_10_Signal,买入卖出价格均选择昨日收盘价(因为根据昨日的买卖信号列的值决定第二天的买卖操作,在开盘前只知道昨日的收盘价,没法知道第二天的价格,所以用昨日的收盘价来回测更加符合实际情况),买入股数填 100,持续买入打勾,最后点提交:
这里,也可以把买入价格和卖出价格配置为今日开盘 / 收盘价,来感觉一下策略的效果,毕竟实际操盘时是人工操作,可以灵活选用第二天当时发生的实际价格。
4 双均线策略——使用内置指标
从头写拼出这些指标还是有些麻烦,特别是那个信号列的公式并不简单。其实这个工作台中已经内置了一些常用的指标,可以直接使用,不用写这些复杂的公式了,比如双均线策略,我们可以用内置指标来定义 MA5 和 MA10:
第一步:点击指标选用按钮:
这时会列出可供选择的指标,点击这些指标文字将会跳出这个指标的解释页面。
目前的策略需要MA- 移动平均线和GDX- 金叉死叉信号这两个指标,勾选后点击确定,指标类型下拉框里就会出现这两个指标了,选择MA- 移动平均线,然后数据列选择收盘,周期填5,MA 输出列名填MA5:
提交后数据显示框中就出现了 MA5 列,可以看到,其值和前面通过 SPL 公式定义的 MA5 的值是一样的。同样的方法,我们把 MA10 也定义了,其它选项都和 MA5 一致,就是周期改成 10,输出列名改成 MA10 即可。
再选择GDX- 金叉死叉信号,短线选MA5,长线选MA10,输出列名填GDX5_10:
提交后可以看到,GDX5_10的返回值和MA5_10_Signal的返回值完全一致:
第二步:定义策略,此时买卖信号列选择GDX5_10, 买卖价格选择昨日收盘价,买入股数填100,持续买入打勾,可以看到回测结果和 SPL 公式定义出来的完全一致:
如果对 MA5 和 MA10 两个均线值不关心,还可以一步到位,使用单个内置指标来完成此策略的定义:
指标选用中勾选MAGDX- 双均线金叉死叉信号:
定义指标:
提交后,可以看到 MAGDX 和前面两种方式定义的指标值完全一样:
5 MACD 背离策略
MACD(Moving Average Convergence and Divergence)是 Geral Appel 于 1979 年提出的,利用收盘价的短期(常用为 12 日)指数移动平均线(EMA)与长期(常用为 26 日)指数移动平均线 (EMA) 之间的聚合与分离状况,对买进、卖出时机作出研判的技术指标。
MACD 从均线指标 EMA 衍化而来,对把握趋势性行情有着很好的应用效果,它的顶底背离是一种经过检验的“抄底逃顶”方法,是不少中长期投资者在实战中都会考虑的指标。
MACD 计算方法:
短线 EMA:短线的指数移动平均,移动窗口通常取 12;
EMA=q* 当前价格 +(1-q)* EMA[-1]
其中 q 是平滑系数,q=2/(移动周期 +1)。
后续的 EMA 都是这样计算,只是移动周期取值不同。
长线 EMA:长线的指数移动平均,移动窗口通常取 26;
长短线的离差 DIFF:短线 EMA- 长线 EMA。
离差平均值 DEA:DIFF 的指数移动平均,移动窗口通常取 9;
MACD:2 *(DIFF - DEA)
下面介绍 MACD 背离买卖策略:
金叉:DIFF 上穿 DEA
死叉:DIFF 下穿 DEA
底背离:股价创新低但 DIFF 没有新低。把最近一次死叉到金叉的区间称为区间 1,把再前一次死叉到金叉的区间称为区间 2。区间 1 的最低股价小于区间 2 的最低股价,区间 1 的最低 DIFF 大于区间 2 的最低 DIFF,此时的金叉作为买入信号。
如下图箭头处,股票价格创新低,dif 指标背离式走高,出现底背离
顶背离:股价创新高但 DIFF 没有新高。把最近一次金叉到死叉的区间称为区间 3,把再前一次金叉到死叉的区间称为区间 4。区间 3 的最高股价大于区间 4 的最高股价,区间 3 的最高 DIFF 小于区间 4 的最高 DIFF,此时的死叉作为卖出信号。
如下图箭头处,股票价格还在创新高,但 dif 指标背离式走低,出现顶背离。
基于上述的算法,我们在指标选用中勾选如下三个内置指标:
其中 MACD 指标返回三个值:
然后再定义 GDX:
GDX 的定义用到了 DIF 和 DEA,最后再定义 DVG:
有了上述指标,我们来定义策略,此时涉及到提前读多少天数据的问题,根据上述算法,为了正确计算第一天的信号值,需要确保 MACD 指标的初始值稳定。MACD(默认参数 12,26,9)的计算涉及以下步骤:
EMA12 和 EMA26:需要足够的历史数据使指数移动平均线(EMA)收敛。通常需要:
EMA12:至少 12*3=36 个交易日(3 倍周期)
EMA26:至少 26*3=78 个交易日
DEA(信号线):MACD 的 9 日 EMA(即 DEA)需要额外 9*3=27 个交易日的数据稳定。
顶底背离检测:为了识别价格与 MACD 的背离,通常需要至少一个完整的波动周期(例如 1-3 个月),因此建议额外提供 60 个交易日以上的数据。
建议:
最低要求:回测开始前至少提供110个交易日的历史数据(覆盖 78+27 个交易日,并留有余量)。
理想情况:提供200个交易日以上的数据,确保 EMA 充分收敛,且能捕捉到前期的价格波动趋势。
原因:
若数据不足,初期 EMA 计算不准确,可能导致 MACD/DIF 值失真,进而产生虚假背离信号。
顶底背离是相对历史高低点的比较,足够的历史数据能避免边界误差。
这里我们选择提前读 200 天的数据,按如下方式定义策略:
提交后可以发现,如果回测区间是 2022 年,则全年没有买入,如果回测区间是 2023 年,则有两笔买卖,年收益率达到 6.09%,说明此策略还不错,能躲开熊市:
MACD 顶底背离策略也有单个的内置指标,如果对 DIF/DEA 等指标不关心的话,也可以用单个指标直接算出:
从指标选用中勾选DVGMACD-MACD 顶底背离信号:
然后在指标类型下拉框中选择DVGMACD-MACD 顶底背离信号,数据列和中长短周期均用缺省值,DVG 输出列填DVGMACD:
提交后,在买卖信号列下拉框中选择DVGMACD,买入股数填100,持续买入打勾,买卖价格选择昨日收盘价:
6 平仓
平仓是指投资者通过反向交易(如卖出已持有的多头头寸或买入回补空头头寸)将现有持仓了结的行为,其目的是终止当前头寸的市场风险暴露,实现盈利或止损。平仓是交易流程中的关键环节,其触发条件可基于价格信号、时间周期、风险控制或策略规则等,直接影响策略的盈亏结果和资金利用率。在回测中,平仓逻辑需与实际交易场景一致,并考虑滑点、手续费等摩擦成本。
这里提供了两种平仓方式:
固定比例止盈止损
适用场景:趋势跟踪或波段交易策略。
逻辑:当收益或亏损达到预设阈值时平仓(如盈利 10% 止盈,亏损 5% 止损)。
作用:锁定利润、控制单笔损失。
固定持有期
适用场景:统计套利或均值回归策略。
逻辑:持仓 N 天后强制平仓(如配对交易中 5 天后平仓)。
作用:避免长期暴露风险,匹配策略假设的时间框架。
我们以 601985 这支股票为例做如下配置:
可以看到,当达到止盈止损阈值或最长持仓日时,股票就会被强制卖出,如果不配置平仓选项,结果如下:
此时会发现因为一直不满足卖出条件,所以股票一直处于持仓中。
这里还提供了一个选项:多次买入分别平仓,其含义是针对止盈幅度、止损幅度、最长持仓日三个属性,如果此项勾选,则每笔交易独立核算,如果不勾选,则价格按所有持仓的均价,最长持仓日按最后一笔买入日期计算。
我们可以做个简单的对比,就用刚才的配置,分别把多次买入分别平仓打勾和不打勾:
可以看出,如果分别平仓,则单笔计算是否符合平仓条件,单笔卖出;如果不分别平仓,则会按照持仓股票统一计算均价和最后一笔交易的最长持仓日,再判断是否平仓,一旦满足,全部清仓。
7 指数比较
策略的好坏可以通过将回测结果和指数做一个对比,看看表现如何,这里可以使用指数比较功能。当前策略提交后,在界面右下角选择上证 50 指数:
然后点击指数比较按钮:
即可在新窗口看到当前策略和选定指数的直观图形对比:
从图上可以看出,使用 MACD 顶底背离策略,在 2023 年可以跑赢上证 50 指数。
8 多票模式以及结果查看
还可以同时回测多只股票:
在弹出框中输入多只股票代码,用英文逗号分隔:
点击开始回测按钮后,可以在数据显示框里同时看到每只股票的回测结果:
此时,右边的回测结果是这几只股票的合计值。需要注意的是,这里的占用资金并不是简单的相加,而是整个回测时间区间里曾经被占用的最大资金数。
如果发现其中某只股票的结果不如期望,想查看一下明细的买卖记录,可以在股票代码下拉框里切换选择:
这时候,中间的数据且就会显示出单票时的买卖记录和持仓情况。
如果想回到前面的多只股票回测结果显示界面,点左下角的多票结果按钮:
9 仓位控制
量化交易中,仓位管理是平衡风险与收益的关键。如果仓位过重,一旦市场走势不利,可能遭受巨大损失。而仓位过轻,又可能错过盈利机会。合适的仓位能在风险和收益间找到平衡,使收益稳定增长。不同的市场环境对仓位管理要求不同。在牛市时,适当增加仓位可以获取更多收益。但在熊市或者震荡市时,就需要降低仓位来规避风险。
我们主要采用两种仓位管理方法:
固定金额法:在这种方法中,每次交易投入固定金额的资金。这种方法简单易行,但可能不够灵活,无法根据市场情况和交易者的风险承受能力进行调整。
固定比例法:每次交易投入账户总资金的固定百分比。这种方法使得随着账户价值的增长或减少,交易仓位大小也会相应调整。
在多票回测弹出窗口中勾选是否需要仓位控制,输入总资金数,每次买入比例或者每次买入金额:
点击开始回测后,数据显示区域会显示这几只股票的买入卖出情况:
把鼠标停留在持仓 / 买入 / 卖出的数字上,即可显示当前持仓或买入 / 卖出交易的股票明细情况。
10 信号输出与实操
在实操时如何用策略来指导下单?这里所讲的策略都是离线策略,适用于低频交易。在离线策略中,可由系统计算出下单信号,然后人工操作下单买卖。这样我们只需在系统中根据策略计算出当天是否有下单信号就可以了,此时可以使用信号输出的功能:
弹出窗口中选择昨天或今天的日期,然后点击计算:
可以看到界面上列出了该日期下信号为 1 或 -1 的股票记录,根据此输出可以很方便地进行今天或第二天的操作。
附录 1 界面元素速查
股票代码: 整数,如 1 表示 sz.000001, 600000 表示 sh.600000。
复权:前复权:保持新时间点的价格不变,对历史时间点的价格进行调整,使得股价连续。后复权:保持早期时间点价格不变,调整后续时间点的价格。
开始:需要回测的起始时间。
结束:需要回测的结束时间。
提前读数:买卖触发时机以及买卖价格,是由头几天或者更早的数据计算而来,而不同的策略需要用到的历史数据的区间不同,所以由用户自行根据策略的需求设置提前读几天的数。
显示:是否把提前读的数显示出来。
左轴右轴:统计图的Y轴,左右轴均可多选。X轴固定为日期。
买卖信号列:用SPL公式自定义指标列,当指标列返回1时表示买入,-1表示卖出,0表示不操作。特别强调,今天的信号列返回值,用于明天的买入卖出操作。
买入价格/卖出价格:如果头天算出来买卖信号列的值为1或-1,则第二天会用买入价格/卖出价格执行买卖操作。但是,如果第二天的最低价格高于买入价格,或最高价格低于卖出价格,则买卖操作执行失败。因为这里主要做基于日线的离线策略,原则上不能使用未来信息,因此在今日交易中会缺省使用昨日收盘价,也可以改成今日收盘价来感觉策略的效果。
买入股数:一次买入操作时买入的股数。此配置和买入金额互斥。
买入金额:一次买入操作时买入的金额。此配置和买入股数互斥。
最大持仓数:为空表示不限制持仓数量,碰到信号合适就会买入;大于等于 1 时,若当前持仓小于这个数时,碰到信号合适就会买入,否则将拒绝买入。
止盈幅度:当前盈利百分比达到配置值时,不管卖出信号列返回值多少,都在第二天强制执行卖出操作。
止损幅度:当前损失百分比达到配置值时,不管卖出信号列返回值多少,都在第二天强制执行卖出操作。
最长持仓日:买入后,持续持仓日数达到配置值,不管卖出信号列返回值多少,都在第二天强制执行卖出操作。
多次买入分别平仓:针对止盈幅度、止损幅度、最长持仓日三个属性,如果此项勾选,则每笔独立核算,如果不勾选,则价格按所有持仓的均价,最长持仓日按最后一笔买入日期计算。
上一交易行/下一交易行:左侧数据的当前选中行自动滚动到 上一个/下一个 有买入卖出交易的行。
信号输出:输出指定日期买卖信号列的返回值。
多票回测:同时对多只股票进行回测操作。
是否需要仓位管理:此选项不勾时,以下三个参数无效。
总资金数:当占用资金超过此值,不再执行买入
每次买入比例:单笔买入的金额占总资金数的比例。
每次买入金额:单笔买入的金额
指标选用:选择内置的指标计算函数,选择后会自动添加到右侧下拉框中,之后在右侧下拉框选择需要定义的指标类型,下方出现对应的参数,根据需要填写即可。
SPL公式:
输出列类型:
普通:主要用于二次计算,如定义输出列名为median,表达式为:(最高+最低)/2,其含义为当天价格区间的中位数。
买卖信号:返回1表示触发买入,返回-1表示触发卖出,返回0表示不操作。此处定义完,才会在上面的买卖信号列下拉框中出现。
买卖价格:若按头天的收盘价或者当天的开盘价买卖,则不需要定义,直接在买卖价格下拉框中选择即可,其它情况需要先定义,然后才会出现在买卖价格下拉框里。特别强调,今日下单是用昨日算出的价格。
保存/打开:将当前设计的策略保存到本地(json 格式),下次可以直接打开使用。
多票结果:使用多票回测时,若想同时看多票的回测结果,可点此按钮;若想切换到单票的明细,可在左上角的股票代码下拉框里选择某只股票即可。
附录 2 常用 SPL 公式语法
同日内的运算
1、 当日价格区间 = 最高 - 最低
定义界面:
说明:SPL 的四则运算符大体和 excel 一致,少量会有不同,这里列出 excel 和 SPL 的异同:
相同之处
1) 基本运算符相同:+-*/ > >= < <=
2) 运算优先级相同:乘除法优先于加减法,可用()改变顺序
不同之处
特性 |
Excel |
集算器 SPL |
幂运算 |
^ |
power(),如 power(2,3) |
取模运算 |
MOD() |
% (如 5%2 返回 1) |
布尔值 |
TRUE/FALSE |
true/false(小写 ) |
比较运算 |
<> |
!= |
空值 |
用 NA() 或空单元格或 NULL |
null(小写 ) |
大小写 |
大小写不敏感 |
大小写敏感,大部分函数和关键词小写,少数大写 |
逻辑运算符与 |
AND() |
&& (如收盘 >=5 && 收盘 <=10) |
或 |
OR() |
|| (如收盘 <=5 || 收盘 >=10) |
非 |
NOT() |
! (如买卖信号列!=0) |
sum |
sum(A1:C5) sum(A1,B3,C5) sum(A1:C5,B6,B7) |
[A1:C5].sum() sum(A1,B3,C5) [A1:C5].sum()+B6+B7 |
count,avg,max,min,mode |
同上 |
同上 |
2、 平滑波动率 =ln(最高 / 最低)*10
说明:ln()为自然对数函数
引用以前的信息
3、 涨跌幅=(收盘-收盘[-1])/收盘[-1]
收盘[-1]表示昨日收盘价,同理,收盘[-2]表示前天的收盘价,依此类推
引用以前多日的信息与集合运算
4、 MA5=收盘[-4:0].avg()
收盘[-4:0]表示前四天和今天的收盘价组成的集合,-4表示从前四天开始,0表示到今天为止。avg()表示计算平均值,因此 收盘[-4:0].avg()为5日均线。同理,若要算9日均线,可以写成收盘[-8:0].avg()。
如果要算前四天到昨天为止的收盘价的均价,可以写成收盘[-4:-1].avg(),-1表示到昨天为止。
avg是聚合函数,可以针对集合运算,其语法规则为(A为集合):
和avg的语法规则完全一致的聚合函数还有:sum求和,max最大值,min最小值,count计数, mode出现次数最多的成员。这里不再一一赘述。
5、 ME5=收盘[-4,0].median()
说明:median()函数计算中位数,中位数比简单平均更能抵抗极端值。median函数语法如下:
函数释义:将序列A根据其长度平均分成n段,返回第k段与第k+1段的分界值,有参数x时,先对A计算表达式x,然后再分段。
k省略n不省略时,将各段的分界值组成序列返回。
k、n参数全省略时,如果序列长度是奇数返回中间位置的成员值;如果序列长度是偶数返回中间两个成员的平均值。对于不能平均分段的序列采取逻辑分段。
6、 avgTop15_5=收盘[-14:0].top(-5).avg()
说明:计算过去15天收盘价中最高的5个的平均值,如果要计算最低的5个,可以写成收盘[-14:0].top(5).avg()
7、 mTop15_5=~[-14:0].top(-5,收盘,最低).avg()
说明:计算过去15天中收盘价最高的5天的最低价平均值。这里,~表示当前行,~[-14:0]表示过去15天的行,top(-5,收盘,最低)返回收盘价最高的五天的最低价组成的集合。
8、 STD20=var@sr(收盘[-19:0])
说明:计算过去20日内收盘价的标准差。var()函数计算总体方差,@s表示计算样本方差,@r表示开方,@sr可以结合使用,即为标准差。
9、 AvgGain=涨跌幅[-13:0].select(~>0).avg()
说明:选出过去14天中涨价的那些天的涨幅平均值,select为过滤函数。~表示集合涨跌幅[-13:0]的当前成员。
10、 AvgGain2=涨跌幅[-13:0].select(~>0.01 && ~<0.9).avg()
说明:选出过去14天中涨幅位于0.01-0.09之间的那些天的涨幅平均值
11、 mAvg9=~[-15:-1].select(最高>9).avg(收盘)
说明:选出最高价超过9的那些天,计算其收盘价的均值。这里,~表示当前行,~[-15:-1]表示过去15天的行,对着行进行过滤时,select中的过滤表达式可以直接引用列名。select的返回结果也是行,所以avg函数要对收盘价进行计算的话,也在参数中直接引用收盘列名。
12、 恐慌贪婪指数= 2/(1+exp(-(成交量-成交量[-5:-1].avg())/成交量[-5:-1].avg()))-1
说明:exp()函数计算e的次幂。
逻辑判断
13、 if(收盘<5,1,0)
说明:当收盘价小于5时,返回1,否则返回0,此函数规则和excel一致。
14、 if(收盘<5:1,收盘>8:-1;0)
说明:当收盘价小于5时,返回1,当收盘价大于8时返回-1,否则返回0。此函数和excel的ifs函数功能类似,上述表达式用excel的ifs写出来为:ifs(收盘<5,1,收盘>8,-1,0)