Estratégia de Comércio de Dual Rail de Oma e Apollo

Autora:ChaoZhang, Data: 2023-11-02 17:09:35
Tags:

img

Resumo

Esta estratégia combina dois principais indicadores técnicos: o indicador Oma e o indicador Apollo para implementar a negociação dual-rail de posições longas e curtas. Sua ideia básica é encontrar oportunidades de retração de curto prazo quando a tendência de médio e longo prazo é julgada de alta para estabelecer posições longas.

Princípio da estratégia

Esta estratégia utiliza médias móveis de 50 dias e 200 dias para determinar a tendência de médio e longo prazo.

Em seguida, a estratégia usa o indicador Oma para localizar oportunidades de reversão de preços a curto prazo. O indicador Oma inclui linhas %K e %D, que são os resultados do indicador RSI suavizado por uma média móvel simples.

Além disso, para filtrar mais sinais falsos, esta estratégia também incorpora o indicador Apollo. O indicador Apollo exibe os pontos extremos dos valores %D da linha K. Quando %K forma uma nova baixa, isso significa que a força de rebote é relativamente fraca. Quando forma uma nova alta, isso significa que a força de rebote é relativamente forte. Combinado com os sinais do indicador Oma, isso pode melhorar ainda mais a precisão da entrada.

Especificamente, em uma tendência de alta, esta estratégia verificará a nova informação de ponto alto ao mesmo tempo em que o indicador Oma mostra uma oportunidade abaixo da área de sobrecompra, para confirmar a força do rebote.

Através do processo acima referido, esta estratégia aproveita plenamente os pontos fortes do julgamento da tendência a médio e longo prazo e dos indicadores de reversão a curto prazo para construir um sistema de negociação de dois trilhos estável.

Vantagens da estratégia

  1. A estratégia combina a negociação de tendência e a negociação de contra-tendência, utilizando tanto o julgamento da tendência como os indicadores de reversão, formando um quadro de negociação híbrido estável.

  2. Através da filtragem de indicadores duplos, a taxa de sinal falso pode ser reduzida e a confiabilidade dos sinais melhorada.

  3. Os parâmetros da estratégia são relativamente simples, fáceis de entender e otimizar, adequados para negociação quantitativa.

  4. O desempenho da estratégia é robusto, com boas características de taxa de ganho e de relação risco/recompensa.

  5. Ao adoptarem binários para longos e curtos, as oportunidades comerciais podem ser obtidas continuamente sem estarem limitadas a uma única direcção.

Riscos da Estratégia

  1. Como estratégia de reversão, podem ocorrer perdas consecutivas quando a tendência muda.

  2. A estratégia requer um controle emocional relativamente elevado do comerciante, que precisa suportar um certo nível de drawdown.

  3. Alguns parâmetros, como os períodos de média móvel, implicam uma certa subjetividade e precisam ser determinados através de backtesting e otimização.

  4. Os indicadores Oma e Apollo têm alguma sensibilidade a flutuações anormais e podem falhar em condições extremas de mercado.

  5. Esta estratégia é mais adequada para mercados voláteis de faixa de variação e pode apresentar um desempenho inferior em mercados com tendências fortes.

Os riscos podem ser mitigados ajustando adequadamente o período da média móvel para introduzir a filtragem de tendências e adicionando stop loss/take profit.

Orientações de otimização

  1. Ensaiar diferentes combinações de parâmetros para obter melhores definições de parâmetros, por exemplo, utilizando médias móveis de suavização EWMA.

  2. Adicionar indicadores de volume ou BV para avaliar a divergência que podem ajudar a verificar a fiabilidade do sinal.

  3. Adicionar índices de volatilidade como o VIX como indicadores de monitorização, para reduzir o tamanho da posição quando o mercado está em pânico.

  4. Otimizar as estratégias de stop loss/take profit, como a adoção de ATR stop loss dinâmico.

  5. Introduzir algoritmos de aprendizagem de máquina para otimizar dinamicamente as definições de parâmetros.

  6. Adicionar modelos multifatores para melhorar a qualidade do sinal.

Resumo

Em geral, esta é uma estratégia de negociação quantitativa estável e eficiente. Combina o julgamento da tendência e indicadores de reversão, e adota a verificação dupla usando os indicadores Oma e Apollo, que podem efetivamente descobrir oportunidades de reversão de preços a curto prazo. Em comparação com o uso de sistemas puramente de tendência ou reversão, esta forma de estratégia é mais robusta com controle de retirada superior e é uma estratégia de negociação quantitativa recomendada. É claro que os usuários também precisam estar cientes dos riscos envolvidos e usar otimização de parâmetros, stop loss / take profit, identificação de regime de mercado etc. para controlar os riscos e alcançar o melhor desempenho.


/*backtest
start: 2023-10-25 00:00:00
end: 2023-10-28 00:00:00
period: 5m
basePeriod: 1m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © PtGambler

//@version=5
strategy("2 EMA + Stoch RSI + ATR [Pt]", shorttitle = "2EMA+Stoch+ATR", overlay=true, initial_capital = 10000, default_qty_type = strategy.percent_of_equity, default_qty_value = 100, calc_on_order_fills = false, max_bars_back = 500)

// ********************************** Trade Period / Strategy Setting **************************************
startY = input(title='Start Year', defval=2011, group = "Backtesting window")
startM = input.int(title='Start Month', defval=1, minval=1, maxval=12, group = "Backtesting window")
startD = input.int(title='Start Day', defval=1, minval=1, maxval=31, group = "Backtesting window")
finishY = input(title='Finish Year', defval=2050, group = "Backtesting window")
finishM = input.int(title='Finish Month', defval=12, minval=1, maxval=12, group = "Backtesting window")
finishD = input.int(title='Finish Day', defval=31, minval=1, maxval=31, group = "Backtesting window")
timestart = timestamp(startY, startM, startD, 00, 00)
timefinish = timestamp(finishY, finishM, finishD, 23, 59)

// ******************************************************************************************

group_ema = "EMA"
group_stoch = "Stochastic RSI"
group_atr = "ATR Stoploss Finder"

// ----------------------------------------- 2 EMA -------------------------------------

ema1_len = input.int(50, "EMA Length 1", group = group_ema)
ema2_len = input.int(200, "EMA Length 2", group = group_ema)

ema1 = ta.ema(close, ema1_len)
ema2 = ta.ema(close, ema2_len)

plot(ema1, "ema1", color.white, linewidth = 2)
plot(ema2, "ema2", color.orange, linewidth = 2)

ema_bull = ema1 > ema2
ema_bear = ema1 < ema2


// -------------------------------------- Stochastic RSI -----------------------------

smoothK = input.int(3, "K", minval=1, group = group_stoch)
smoothD = input.int(3, "D", minval=1, group = group_stoch)
lengthRSI = input.int(14, "RSI Length", minval=1, group = group_stoch)
lengthStoch = input.int(14, "Stochastic Length", minval=1, group = group_stoch)
src = close
rsi1 = ta.rsi(src, lengthRSI)
k = ta.sma(ta.stoch(rsi1, rsi1, rsi1, lengthStoch), smoothK)
d = ta.sma(k, smoothD)

var trigger_stoch_OB = k > 80
var trigger_stoch_OS = k < 20

stoch_crossdown = ta.crossunder(k, d)
stoch_crossup = ta.crossover(k, d)

P_hi = ta.pivothigh(k,1,1)
P_lo = ta.pivotlow(k,1,1)

previous_high = ta.valuewhen(P_hi, k, 1)
previous_low = ta.valuewhen(P_lo, k, 1)
recent_high = ta.valuewhen(P_hi, k, 0)
recent_low = ta.valuewhen(P_lo, k, 0)

// --------------------------------------- ATR stop loss finder ------------------------

length = input.int(title='Length', defval=14, minval=1, group = group_atr)
smoothing = input.string(title='Smoothing', defval='EMA', options=['RMA', 'SMA', 'EMA', 'WMA'], group = group_atr)
m = input.float(0.7, 'Multiplier', step = 0.1, group = group_atr)
src1 = input(high, "Source for upper band", group = group_atr)
src2 = input(low, "Source for lower band", group = group_atr)

showatr = input.bool(true, 'Show ATR Bands', group = group_atr)
collong = input.color(color.purple, 'Long ATR SL', inline='1', group = group_atr)
colshort = input.color(color.purple, 'Short ATR SL', inline='2', group = group_atr)

ma_function(source, length) =>
    if smoothing == 'RMA'
        ta.rma(source, length)
    else
        if smoothing == 'SMA'
            ta.sma(source, length)
        else
            if smoothing == 'EMA'
                ta.ema(source, length)
            else
                ta.wma(source, length)

a = ma_function(ta.tr(true), length) * m
up = ma_function(ta.tr(true), length) * m + src1
down = src2 - ma_function(ta.tr(true), length) * m

p1 = plot(showatr ? up : na, title='ATR Short Stop Loss', color=colshort)
p2 = plot(showatr ? down : na, title='ATR Long Stop Loss', color=collong)

// ******************************* Profit Target / Stop Loss *********************************************

RR = input.float(2.0, "Reward to Risk ratio (X times SL)", step = 0.1, group = "Profit Target")

var L_PT = 0.0
var S_PT = 0.0
var L_SL = 0.0
var S_SL = 0.0

BSLE = ta.barssince(strategy.opentrades.entry_bar_index(0) == bar_index)

if strategy.position_size > 0 and BSLE == 1
    L_PT := close + (close-down)*RR
    L_SL := L_SL[1]
    S_PT := close - (up - close)*RR
    S_SL := up
else if strategy.position_size < 0 and BSLE == 1
    S_PT := close - (up - close)*RR
    S_SL := S_SL[1]
    L_PT := close + (close-down)*RR
    L_SL := down
else if strategy.position_size != 0
    L_PT := L_PT[1] 
    S_PT := S_PT[1]
else
    L_PT := close + (close-down)*RR
    L_SL := down
    S_PT := close - (up - close)*RR
    S_SL := up

entry_line = plot(strategy.position_size != 0 ? strategy.opentrades.entry_price(0) : na, "Entry Price", color.white, linewidth = 1, style = plot.style_linebr)

L_PT_line = plot(strategy.position_size > 0 and BSLE > 0 ? L_PT : na, "L PT", color.green, linewidth = 2, style = plot.style_linebr)
S_PT_line = plot(strategy.position_size < 0 and BSLE > 0 ? S_PT : na, "S PT", color.green, linewidth = 2, style = plot.style_linebr)

L_SL_line = plot(strategy.position_size > 0 and BSLE > 0 ? L_SL : na, "L SL", color.red, linewidth = 2, style = plot.style_linebr)
S_SL_line = plot(strategy.position_size < 0 and BSLE > 0 ? S_SL : na, "S SL", color.red, linewidth = 2, style = plot.style_linebr)

fill(L_PT_line, entry_line, color = color.new(color.green,90))
fill(S_PT_line, entry_line, color = color.new(color.green,90))
fill(L_SL_line, entry_line, color = color.new(color.red,90))
fill(S_SL_line, entry_line, color = color.new(color.red,90))


// ---------------------------------- strategy setup ------------------------------------------------------

var L_entry_trigger1 = false
var S_entry_trigger1 = false

L_entry_trigger1 := ema_bull and close < ema1 and k < 20 and strategy.position_size == 0
S_entry_trigger1 := ema_bear and close > ema1 and k > 80 and strategy.position_size == 0

L_entry1 = L_entry_trigger1[1] and stoch_crossup and recent_low > previous_low
S_entry1 = S_entry_trigger1[1] and stoch_crossdown and recent_high < previous_high

//debugging
plot(L_entry_trigger1[1]?1:0, "L Entry Trigger")
plot(stoch_crossup?1:0, "Stoch Cross Up")
plot(recent_low > previous_low?1:0, "Higher low")

plot(S_entry_trigger1[1]?1:0, "S Entry Trigger")
plot(stoch_crossdown?1:0, "Stoch Cross down")
plot(recent_high < previous_high?1:0, "Lower high")

if L_entry1
    strategy.entry("Long", strategy.long)

if S_entry1
    strategy.entry("Short", strategy.short)

strategy.exit("Exit Long", "Long", limit = L_PT, stop = L_SL, comment_profit = "Exit Long, PT hit", comment_loss = "Exit Long, SL hit")
strategy.exit("Exit Short", "Short", limit = S_PT, stop = S_SL, comment_profit = "Exit Short, PT hit", comment_loss = "Exit Short, SL hit")

//resetting triggers
L_entry_trigger1 := L_entry_trigger1[1] ? L_entry1 or ema_bear or S_entry1 ? false : true : L_entry_trigger1
S_entry_trigger1 := S_entry_trigger1[1] ? S_entry1 or ema_bull or L_entry1 ? false : true : S_entry_trigger1

//Trigger zones
bgcolor(L_entry_trigger1 ? color.new(color.green ,90) : na)
bgcolor(S_entry_trigger1 ? color.new(color.red,90) : na)

Mais.