A Estratégia de Reversão BollTrade Bollinger é uma estratégia StockSharp de alto nível convertida do clássico consultor especialista BollTrade MetaTrader. Ele negocia um único instrumento usando bandas Bollinger e espera por variações de preço além das bandas, além de um buffer de pip adicional. Quando uma vela fecha acima da banda superior a estratégia abre uma posição curta, e quando uma vela fecha abaixo da banda inferior ela abre uma posição longa. Todas as decisões são tomadas em velas finalizadas para evitar reagir a dados incompletos.
Lógica de negociação
Assine o tipo de vela configurado e calcule Bollinger Bandas com período e desvio selecionados.
Calcule uma compensação de preço adicional expressa em unidades pip para imitar o buffer original que forçou as negociações a entrarem mais profundamente no território de sobrecompra/sobrevenda.
Quando o preço de fechamento de uma vela concluída estiver abaixo da banda inferior menos o deslocamento, abra uma posição longa. Quando estiver acima da banda superior mais o deslocamento, abra uma posição curta.
Para cada negociação aberta, a estratégia armazena níveis de stop-loss e take-profit definidos em unidades pip. Essas saídas emulam o consultor especialista original que fechava posições quando o lucro ou perda flutuante cruzava distâncias de pip predefinidas.
As posições são fechadas quando o intervalo da vela ultrapassa o limite de stop-loss ou de take-profit. Nenhum dimensionamento ou pirâmide adicional é executado.
Gestão de capital
O parâmetro Lots define o tamanho da posição base.
Quando LotIncrease está ativado, o volume é dimensionado proporcionalmente ao valor atual do portfólio em relação ao valor observado no início da estratégia, até um limite de segurança de 500 lotes. Isso reproduz a lógica de dimensionamento vinculada ao saldo da versão MetaTrader.
Parâmetros
Parâmetro
Descrição
Take Profit (pips)
Distância em pips usada para calcular o nível de lucro a partir do preço de entrada. Defina como zero para desativar a saída de lucro.
Stop Loss (pips)
Distância em pips usada para calcular o nível de stop loss a partir do preço de entrada. Defina como zero para desativar a saída de stop loss.
Deslocamento de banda
Distância adicional de pip adicionada além da banda Bollinger antes de abrir uma negociação.
Bollinger Período
Número de velas usadas para a média móvel das bandas Bollinger.
Bollinger Desvio
Multiplicador de desvio padrão para a largura das bandas Bollinger.
Volume Básico
Volume base de negociação em lotes.
Volume de escala
Quando ativado, aumenta o volume de pedidos com base no crescimento do valor do portfólio.
Tipo de vela
Tipo de vela (período de tempo) usado para geração de sinal.
Notas
A estratégia funciona apenas com velas finalizadas e, portanto, precisa de dados históricos para aquecimento antes da negociação ao vivo.
Os níveis de stop-loss e take-profit são avaliados em intervalos de velas, o que se aproxima da lógica original baseada em ticks, permanecendo compatível com o nível superior API.
Os recursos de proteção da estrutura StockSharp (StartProtection) são ativados para proteger contra exposição acidental à posição quando a estratégia para inesperadamente.
using System;
using System.Collections.Generic;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;
namespace StockSharp.Samples.Strategies;
/// <summary>
/// Bollinger Bands reversion strategy.
/// Buys when price closes below lower band, sells when above upper band.
/// Uses middle band as exit target.
/// </summary>
public class BollTradeBollingerReversionStrategy : Strategy
{
private readonly StrategyParam<int> _bollingerPeriod;
private readonly StrategyParam<decimal> _bollingerWidth;
private readonly StrategyParam<DataType> _candleType;
public int BollingerPeriod { get => _bollingerPeriod.Value; set => _bollingerPeriod.Value = value; }
public decimal BollingerWidth { get => _bollingerWidth.Value; set => _bollingerWidth.Value = value; }
public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }
public BollTradeBollingerReversionStrategy()
{
_bollingerPeriod = Param(nameof(BollingerPeriod), 20)
.SetDisplay("BB Period", "Bollinger Bands period", "Indicators");
_bollingerWidth = Param(nameof(BollingerWidth), 0.5m)
.SetDisplay("BB Width", "Bollinger Bands width", "Indicators");
_candleType = Param(nameof(CandleType), TimeSpan.FromHours(4).TimeFrame())
.SetDisplay("Candle Type", "Candle timeframe", "General");
}
/// <inheritdoc />
public override IEnumerable<(Security sec, DataType dt)> GetWorkingSecurities()
{
return [(Security, CandleType)];
}
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
}
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
var bb = new BollingerBands
{
Length = BollingerPeriod,
Width = BollingerWidth
};
var subscription = SubscribeCandles(CandleType);
subscription
.BindEx(bb, ProcessCandle)
.Start();
}
private void ProcessCandle(ICandleMessage candle, IIndicatorValue bbValue)
{
if (candle.State != CandleStates.Finished)
return;
if (!bbValue.IsFinal)
return;
var bb = (BollingerBandsValue)bbValue;
var upper = bb.UpBand;
var lower = bb.LowBand;
var middle = bb.MovingAverage;
if (upper == null || lower == null || middle == null)
return;
var close = candle.ClosePrice;
var upperVal = upper.Value;
var lowerVal = lower.Value;
var midVal = middle.Value;
// Buy when close below lower band (oversold)
if (close < lowerVal && Position <= 0)
{
if (Position < 0)
BuyMarket();
BuyMarket();
}
// Sell when close above upper band (overbought)
else if (close > upperVal && Position >= 0)
{
if (Position > 0)
SellMarket();
SellMarket();
}
}
}
import clr
clr.AddReference("StockSharp.Messages")
clr.AddReference("StockSharp.Algo")
clr.AddReference("StockSharp.Algo.Indicators")
clr.AddReference("StockSharp.Algo.Strategies")
from System import TimeSpan, Math
from StockSharp.Messages import DataType, CandleStates
from StockSharp.Algo.Indicators import BollingerBands
from StockSharp.Algo.Strategies import Strategy
class boll_trade_bollinger_reversion_strategy(Strategy):
"""Bollinger Bands reversion strategy.
Buys when price closes below lower band, sells when above upper band."""
def __init__(self):
super(boll_trade_bollinger_reversion_strategy, self).__init__()
self._bollinger_period = self.Param("BollingerPeriod", 20) \
.SetDisplay("BB Period", "Bollinger Bands period", "Indicators")
self._bollinger_width = self.Param("BollingerWidth", 0.5) \
.SetDisplay("BB Width", "Bollinger Bands width", "Indicators")
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromHours(4))) \
.SetDisplay("Candle Type", "Candle timeframe", "General")
@property
def CandleType(self):
return self._candle_type.Value
@CandleType.setter
def CandleType(self, value):
self._candle_type.Value = value
@property
def BollingerPeriod(self):
return self._bollinger_period.Value
@property
def BollingerWidth(self):
return self._bollinger_width.Value
def OnReseted(self):
super(boll_trade_bollinger_reversion_strategy, self).OnReseted()
def OnStarted2(self, time):
super(boll_trade_bollinger_reversion_strategy, self).OnStarted2(time)
bb = BollingerBands()
bb.Length = self.BollingerPeriod
bb.Width = self.BollingerWidth
subscription = self.SubscribeCandles(self.CandleType)
subscription.BindEx(bb, self._process_candle).Start()
def _process_candle(self, candle, bb_value):
if candle.State != CandleStates.Finished:
return
if not bb_value.IsFinal:
return
up_band = bb_value.UpBand if hasattr(bb_value, 'UpBand') else None
low_band = bb_value.LowBand if hasattr(bb_value, 'LowBand') else None
if up_band is None or low_band is None:
return
upper = float(up_band)
lower = float(low_band)
close = float(candle.ClosePrice)
# Buy when close below lower band (oversold)
if close < lower and self.Position <= 0:
if self.Position < 0:
self.BuyMarket()
self.BuyMarket()
# Sell when close above upper band (overbought)
elif close > upper and self.Position >= 0:
if self.Position > 0:
self.SellMarket()
self.SellMarket()
def CreateClone(self):
return boll_trade_bollinger_reversion_strategy()