Estratégia de acompanhamento de tendência otimizada para quebra de momentum


Data de criação: 2024-01-17 16:44:30 última modificação: 2024-01-17 16:44:30
cópia: 0 Cliques: 622
1
focar em
1617
Seguidores

Estratégia de acompanhamento de tendência otimizada para quebra de momentum

Visão geral

A estratégia de otimização de ruptura dinâmica é uma estratégia de acompanhamento de tendências baseada em indicadores dinâmicos para geração de sinais de negociação e configuração de stop loss. A estratégia determina a direção da tendência do mercado através do cálculo do preço e do cruzamento da linha média móvel, em combinação com o ATR e o canal LinReg para construir um mecanismo de parada dinâmica.

Princípio da estratégia

  • 1. ZLEMA Moving Average calculado em preços como indicador técnico para determinar a direção da tendência
  • 2. Preço de parada de uma posição longa e um preço de parada de uma posição curta calculados de acordo com o ATR
  • 3. Calcule o indicador CMO para determinar o intervalo de sobrecompra e sobrevenda, em conjunto com a média móvel como sinal de entrada
  • 4. Construção de três grupos de sinais de negociação com base em ATR e média móvel de ruptura
    • Sinais de cruzamento entre a média móvel e o preço de parada
    • Sinais de cruzamento de preços e preços de parada
    • Sinal de cruzamento de preços e médias móveis
  • 5. Controle de ativação de diferentes tipos de sinais através de configurações de parâmetros
  • 6. Configurar o fator de risco e controle de posição para o gerenciamento de risco

A estratégia completa permite um acompanhamento de tendências estável e um stop-loss automático através da aplicação de uma combinação de vários indicadores, garantindo tanto oportunidades de negociação suficientes quanto o controle do risco de negociação.

Análise de vantagens

Utilização de vários conjuntos de indicadores

A estratégia usa uma combinação de vários indicadores, como médias móveis, ATR, CMO, entre outros, que podem ser complementados de forma eficaz, identificando a direção da tendência e julgando com mais precisão e confiança as áreas de supercompra e supervenda.

Paragem dinâmica

O mecanismo de stop loss dinâmico baseado no ATR permite ajustar a posição de stop loss de forma flexível, de acordo com a volatilidade do mercado, controlando efetivamente os perdas individuais.

Uma boa gestão de riscos

A estratégia oferece controle de posição e configuração de fator de risco, que permite definir antecipadamente a proporção de capital máximo de perda, evitando grandes flutuações de capital.

A abundância de sinais de negociação

A estratégia oferece três conjuntos de sinais de negociação, que podem ser melhor avaliados por meio da seleção de combinações de diferentes tipos de sinais ativados.

Análise de Riscos

Frequência de transações excessiva

Quando todos os conjuntos de sinais são ativados, a frequência de negociação pode ser excessiva. Isso pode ser evitado selecionando apenas alguns conjuntos de sinais.

Parâmetros de indicadores sensíveis

O uso de vários conjuntos de indicadores torna a seleção de parâmetros mais complexa, mais sensível à configuração de parâmetros e requer um conjunto ideal de parâmetros cuidadosamente testados.

Redução de sinais de ruptura

Os sinais de negociação baseados apenas no cruzamento do preço e do preço de parada têm um grande alcance de parada, o que pode levar a grandes perdas e retrações individuais. Pode-se optar por usar o sinal de linha média móvel em combinação com ele.

Direção de otimização

Teste diferentes combinações de parâmetros

Optimizar o tipo de média móvel, o parâmetro de duração; otimizar o parâmetro do ciclo ATR; otimizar o parâmetro do CMO. Encontrar a melhor correspondência entre os parâmetros.

Estratégias para otimizar o uso de sinais

Os testes usam apenas os sinais de média móvel, os sinais de preço de parada e os sinais combinados para analisar a melhor estratégia de uso.

Testes de desempenho em diferentes variedades

A retrospectiva é realizada em índices de ações, divisas e variedades de mercadorias, analisando a adequação da estratégia ao tipo de mercado.

Resumir

Esta estratégia utiliza vários indicadores para identificar a direção da tendência, construir um mecanismo de parada de perda e encontrar oportunidades de sobrecompra e sobrevenda. Ajustes podem ser obtidos através de métodos como otimização de parâmetros e seleção de combinações de sinais.

Código-fonte da estratégia
/*backtest
start: 2024-01-09 00:00:00
end: 2024-01-16 00:00:00
period: 5m
basePeriod: 1m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

//@version=4
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © KivancOzbilgic
//developer: @KivancOzbilgic
//author: @KivancOzbilgic

strategy(title="Profit Maximizer PMax", overlay=true,
     pyramiding=0, initial_capital=1000,
     commission_type=strategy.commission.cash_per_order,
     commission_value=0.025, slippage=2)


src = input(hl2, title="Source")
Periods = input(title="ATR Length", type=input.integer, defval=10)
Multiplier = input(title="ATR Multiplier", type=input.float, step=0.1, defval=3.0)
mav = input(title="Moving Average Type", defval="ZLEMA", options=["SMA", "EMA", "WMA", "TMA", "VAR", "WWMA", "ZLEMA", "TSF"])
length =input(10, "Moving Average Length", minval=1)
changeATR= input(title="Change ATR Calculation Method ?", type=input.bool, defval=true)
showsupport = input(title="Show Moving Average?", type=input.bool, defval=true)
showsignalsk = input(title="Show Crossing Signals?", type=input.bool, defval=true)
showsignalsc = input(title="Show Price/Pmax Crossing Signals?", type=input.bool, defval=false)
highlighting = input(title="Highlighter On/Off ?", type=input.bool, defval=true)

usePosSize = input(title="Use Position Sizing?", type=input.bool, defval=true)
riskPerc   = input(title="Risk %", type=input.float, defval=0.5, step=0.25)

// Make input options that configure backtest date range
startDate = input(title="Start Date", type=input.integer,
     defval=1, minval=1, maxval=31)
startMonth = input(title="Start Month", type=input.integer,
     defval=1, minval=1, maxval=12)
startYear = input(title="Start Year", type=input.integer,
     defval=2019, minval=1800, maxval=2100)

endDate = input(title="End Date", type=input.integer,
     defval=1, minval=1, maxval=31)
endMonth = input(title="End Month", type=input.integer,
     defval=12, minval=1, maxval=12)
endYear = input(title="End Year", type=input.integer,
     defval=2021, minval=1800, maxval=2100)
     
// Look if the close time of the current bar
// falls inside the date range
inDateRange = true

atr2 = sma(tr, Periods)
atr= changeATR ? atr(Periods) : atr2
valpha=2/(length+1)
vud1=src>src[1] ? src-src[1] : 0
vdd1=src<src[1] ? src[1]-src : 0
vUD=sum(vud1,9)
vDD=sum(vdd1,9)
vCMO=nz((vUD-vDD)/(vUD+vDD))
VAR=0.0
VAR:=nz(valpha*abs(vCMO)*src)+(1-valpha*abs(vCMO))*nz(VAR[1])
wwalpha = 1/ length
WWMA = 0.0
WWMA := wwalpha*src + (1-wwalpha)*nz(WWMA[1])
zxLag = length/2==round(length/2) ? length/2 : (length - 1) / 2
zxEMAData = (src + (src - src[zxLag]))
ZLEMA = ema(zxEMAData, length)
lrc = linreg(src, length, 0)
lrc1 = linreg(src,length,1)
lrs = (lrc-lrc1)
TSF = linreg(src, length, 0)+lrs
getMA(src, length) =>
    ma = 0.0
    if mav == "SMA"
        ma := sma(src, length)
        ma

    if mav == "EMA"
        ma := ema(src, length)
        ma

    if mav == "WMA"
        ma := wma(src, length)
        ma

    if mav == "TMA"
        ma := sma(sma(src, ceil(length / 2)), floor(length / 2) + 1)
        ma

    if mav == "VAR"
        ma := VAR
        ma

    if mav == "WWMA"
        ma := WWMA
        ma

    if mav == "ZLEMA"
        ma := ZLEMA
        ma

    if mav == "TSF"
        ma := TSF
        ma
    ma
    
MAvg=getMA(src, length)
longStop = MAvg - Multiplier*atr
longStopPrev = nz(longStop[1], longStop)
longStop := MAvg > longStopPrev ? max(longStop, longStopPrev) : longStop
shortStop = MAvg + Multiplier*atr
shortStopPrev = nz(shortStop[1], shortStop)
shortStop := MAvg < shortStopPrev ? min(shortStop, shortStopPrev) : shortStop
dir = 1
dir := nz(dir[1], dir)
dir := dir == -1 and MAvg > shortStopPrev ? 1 : dir == 1 and MAvg < longStopPrev ? -1 : dir
PMax = dir==1 ? longStop: shortStop
plot(showsupport ? MAvg : na, color=#0585E1, linewidth=2, title="Moving Avg Line")
pALL=plot(PMax, color=color.red, linewidth=2, title="PMax", transp=0)

alertcondition(cross(MAvg, PMax), title="Cross Alert", message="PMax - Moving Avg Crossing!")
alertcondition(crossover(MAvg, PMax), title="Crossover Alarm", message="Moving Avg BUY SIGNAL!")
alertcondition(crossunder(MAvg, PMax), title="Crossunder Alarm", message="Moving Avg SELL SIGNAL!")
alertcondition(cross(src, PMax), title="Price Cross Alert", message="PMax - Price Crossing!")
alertcondition(crossover(src, PMax), title="Price Crossover Alarm", message="PRICE OVER PMax - BUY SIGNAL!")
alertcondition(crossunder(src, PMax), title="Price Crossunder Alarm", message="PRICE UNDER PMax - SELL SIGNAL!")


// Calculate position size
riskEquity  = (riskPerc / 100) * strategy.equity
atrCurrency = (atr(20) * syminfo.pointvalue)
posSize     = usePosSize ? floor(riskEquity / atrCurrency) : 1

//Long
buySignalk = crossover(MAvg, PMax)
plotshape(buySignalk and showsignalsk ? PMax*0.995 : na, title="Buy", text="BuyL", location=location.absolute, style=shape.labelup, size=size.tiny, color=color.green, textcolor=color.white, transp=0)


if(buySignalk and showsignalsk and inDateRange)
    strategy.entry(id="buySignalk", long=true, qty=posSize)
    
sellSignallk = crossunder(MAvg, PMax)
plotshape(sellSignallk and showsignalsk ? PMax*1.005 : na, title="Sell", text="SellL", location=location.absolute, style=shape.labeldown, size=size.tiny, color=color.red, textcolor=color.white, transp=0)

if(sellSignallk and showsignalsk and inDateRange)
    strategy.order(id="sellSignallk", long=false, qty=strategy.position_size)
    
//Short
buySignalc = crossover(src, PMax)
plotshape(buySignalc and showsignalsc ? PMax*0.995 : na, title="Buy", text="BuyS", location=location.absolute, style=shape.labelup, size=size.tiny, color=#0F18BF, textcolor=color.white, transp=0)

if(buySignalc and showsignalsc and inDateRange)
    strategy.entry(id="BuyS", long=false, qty=posSize)

sellSignallc = crossunder(src, PMax)
plotshape(sellSignallc and showsignalsc ? PMax*1.005 : na, title="Sell", text="SellS", location=location.absolute, style=shape.labeldown, size=size.tiny, color=#0F18BF, textcolor=color.white, transp=0)

if(sellSignallc and showsignalsc and inDateRange)
    strategy.order(id="SellS", long=true, qty=abs(strategy.position_size))

mPlot = plot(ohlc4, title="", style=plot.style_circles, linewidth=0,display=display.none)

longFillColor = highlighting ? (MAvg>PMax ? color.green : na) : na
shortFillColor = highlighting ? (MAvg<PMax ? color.red : na) : na

fill(mPlot, pALL, title="UpTrend Highligter", color=longFillColor)
fill(mPlot, pALL, title="DownTrend Highligter", color=shortFillColor)

// Exit open market position when date range ends
if (not inDateRange)
    strategy.close_all()