上一篇我们实现了一个简单的均线策略,本期我们一起来看如何实现一个网格策略。股票网格策略比较简单,相对于可以做多做空的期货,股票就只能做多了。网格策略就只能向下挂买单,分散持仓价格位置,持续低吸。等待到价格反弹逐笔平仓或者全部平仓。

策略设计

策略同样可以使用我们之前使用的程序结构框架,需要做一些修改即可实现一个网格策略。设计策略时要用最简单的设计思路,尽量让程序逻辑简洁,这样便于维护、修改、扩展。考虑到同样可以让策略做多个股票,所以我们对于网格的每个点的差价设置成一个比例,这样我们设置一个参数即可,就不用设置一堆参数,给每个股票都设置具体的网格节点差价。

DiffPricePercent 网格节点差价

可以理解为开仓一次到下一次开仓时的价格差,参数是一个小数,例如设置0.02即代表2%。表示当前价格减去当前价格的2%得出的价格为下一次开仓的价格。对于网格的起始价格应该是可以指定的,所以我们设计了BeginPrices参数。

BeginPrices

参数BeginPrices设计成一个字符串,可以输入一个数组JSON字符串,让策略解析为一个数组结构,在策略初始化时给每只股票的数据结构分配一个网格初始价格。这个起始价格我们可能有时会指定,但是有时又想让以当前价格为起始价格,那怎么办?这个设计很简单,如果需要让以当前价格为初始价格我们就设置-1,代表当前价格。

      // 更新行情数据
      symbols[i].CurrPrice = ticker.Last
      if (symbols[i].BeginPrice == -1) {
          symbols[i].BeginPrice = ticker.Last
      }

我们只用在策略中检测这个起始价格是不是-1,如果是-1,把当前价格赋值给这个变量记录即可。

这些是我们在程序框架基础上添加的2个参数。
策略图表也需要修改,我想要的是这样的效果....我的脑海里出现这样的画面:
股票网格策略-LMLPHP
那就动手实现吧。

图表设计

分析我们的需求,除了普通的K线图表显示以外,我们还需要绘制网格每个价格位置的水平线。所以我们需要根据当前的持仓、DiffPricePercent参数、起始价格等数据去计算当前的网格。以下代码为计算每个网格的价格。

      ...
      var hasPosAmount = posAmount
      var beginPrice = symbols[i].BeginPrice
      var count = 0
      while (true) {
          if (count == 0) {                                  // 第一个点是起始点,给图表配置结构写入对应的数据
              symbols[i].ChartCfg.yAxis.plotLines.push({     // symbols[i].ChartCfg 即当前股票的图表配置变量
                  value: beginPrice,
                  color: 'red',
                  width: 2,
                  label: {
                      text: '起始价格',
                      align: 'center'
                  },
              })
              count++
              continue
          }

          beginPrice = beginPrice - beginPrice * DiffPricePercent          // 计算得出当前节点的价格beginPrice
          hasPosAmount = hasPosAmount - TradeAmount
          symbols[i].ChartCfg.yAxis.plotLines.push({                       // 写入图表配置
              value: beginPrice,
              color: 'blue',
              width: 2,
              label: {
                  text: '节点:' + count,
                  align: 'center'
              },
          })

          if (hasPosAmount < 0) {                                           // 检测到未开仓位置,跳出循环
              _Chart.update(_ArrChart)
              break
          }
          count++
      }

策略交易逻辑

策略交易逻辑比较简单,只要当前价格低于计算出的最后一个网格节点价格,就买入。
如果当前价格高于持仓均价达到持仓均价的2 * DiffPricePercent倍,就卖出。

      if (ticker.Last < beginPrice) {
          // 买入
          Log(contractTypeName, "开多仓", "beginPrice:", beginPrice, "posAmount:", posAmount)
          Buy(exchange, contractTypeName, TradeAmount, ticker.Info)
          symbols[i].State = STATE_LONG
      }
      if (posAmount > 0 && pos.CanCoverAmount > 0 && ticker.Last > pos.Price + pos.Price * DiffPricePercent * 2) {
          // 平仓
          Log(contractTypeName, "平多仓")
          Sell(exchange, contractTypeName, Math.min(pos.CanCoverAmount, posAmount), ticker.Info)
          symbols[i].State = STATE_IDLE
      }

策略初步回测测试

股票网格策略-LMLPHP

股票网格策略-LMLPHP

策略地址

策略仅仅用来学习、研究,策略并未经过实盘测试,实盘慎用。

策略仅仅用于学习交流,交流策略设计思路,互相学习,有兴趣的可以挂一个富途模拟盘测试,不过个人认为网格策略仅仅适用于震荡行情,在股市熊市的时候风险比较大,虽然说股票不存在像期货那样爆仓的风险,但是遇到趋势容易被套牢。使用网格策略,网格大小和预留资金是两个挺重要的因素。

感谢阅读,感谢提出建议及意见。

06-17 15:36