Cette stratégie combine plusieurs moyennes mobiles telles que SMA et EMA pour identifier la direction de la tendance des prix et définit des lignes de stop loss basées sur la percée des prix pour concevoir une stratégie de suivi de la tendance. Lorsque les prix augmentent, elle suit la bande supérieure comme un stop loss; lorsque les prix baissent, elle suit la limite inférieure comme un stop loss. L'avantage de la stratégie est que la combinaison de plusieurs moyennes mobiles peut lisser les données des prix et identifier les tendances; La conception dynamique du stop loss évite les arrêts trop sensibles. Le risque de la stratégie est que la définition de la ligne de stop loss peut être trop lâche pour arrêter la perte à temps.
Cette stratégie utilise le KAMA comme base pour juger de la direction de la tendance, car le KAMA répond aux changements de prix de manière plus sensible et peut identifier les virages à l'avance.
Le paramètre de la ligne de stop-loss de la stratégie est basé sur le prix lui-même et la moyenne mobile. Plus précisément, la ligne de stop-loss ascendante est la moyenne mobile plus une proportion en tant que tampon; la ligne de stop-loss descendante est la moyenne mobile moins une proportion en tant que tampon. Cela permet un stop-loss immédiat lorsque les prix s'inversent.
Les conditions d'entrée sont longues lorsque les prix franchissent la ligne d'arrêt de perte à la hausse de bas en haut; courtes lorsque les prix franchissent la ligne d'arrêt de perte à la baisse de haut en bas.
Le plus grand avantage de cette stratégie est qu'en combinant plusieurs moyennes mobiles, la précision du jugement de tendance peut être améliorée et les faux signaux peuvent être réduits.
En outre, par rapport aux stratégies à indicateur unique, cette stratégie combine les avantages du suivi des tendances et des stratégies de percée.
Le principal risque de cette stratégie est que le réglage de la ligne stop loss peut être trop lâche pour arrêter la perte dans le temps.
En outre, la moyenne mobile elle-même a une hystérésis élevée et ne peut pas réagir immédiatement aux changements de prix.
La stratégie peut être optimisée dans les aspects suivants:
Tester différents paramètres pour les ratios de la ligne stop-loss afin de trouver de meilleures combinaisons de paramètres;
Essayez de faire changer dynamiquement la ligne de stop loss en fonction du degré de fluctuation du marché;
Augmenter les autres indicateurs à évaluer, introduire plus de variables dans la base de stop loss pour améliorer l'adaptabilité de la stratégie;
Optimiser les paramètres de cycle de la moyenne mobile pour trouver le meilleur réglage de cycle pour faciliter les prix.
Dans l'ensemble, cette stratégie est assez robuste, combinant plusieurs moyennes mobiles pour déterminer la direction de la tendance et concevant un mécanisme de stop loss dynamique visant à suivre les tendances.
/*backtest start: 2023-02-22 00:00:00 end: 2024-02-28 00:00:00 period: 1d basePeriod: 1h exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}] */ //@version=5 strategy('Atlantean Trend Signal BUY SELL Strategy', overlay=true) ma_length = input.int(title='Moving Average Length', minval=1, defval=3) percent = input.float(3.3, 'STOP LOSS Percent', step=0.1, minval=0) src = input(title='Source', defval=close) mav = input.string(title="Moving Average Type", defval="KAMA", options=["SMA", "EMA", "WMA", "DEMA", "TMA", "VAR", "WWMA", "ZLEMA", "TSF", "HULL", "TILL", "KAMA"]) T3a1 = 0.7 _type = false //input(false, title='Activate Moving Average Screening Mode') _type1 = false //input(false, title='Activate Moving Average Color Change Screening Mode') activateScreener = input.bool(false, title="Activate Screener?") showsignallabels = input(title='Show Signal Labels?', defval=true) Var_Func(src, ma_length) => valpha = 2 / (ma_length + 1) vud1 = src > src[1] ? src - src[1] : 0 vdd1 = src < src[1] ? src[1] - src : 0 vUD = math.sum(vud1, 9) vDD = math.sum(vdd1, 9) vCMO = nz((vUD - vDD) / (vUD + vDD)) VAR = 0.0 VAR := nz(valpha * math.abs(vCMO) * src) + (1 - valpha * math.abs(vCMO)) * nz(VAR[1]) VAR VAR = Var_Func(src, ma_length) DEMA = 2 * ta.ema(src, ma_length) - ta.ema(ta.ema(src, ma_length), ma_length) Wwma_Func(src, ma_length) => wwalpha = 1 / ma_length WWMA = 0.0 WWMA := wwalpha * src + (1 - wwalpha) * nz(WWMA[1]) WWMA WWMA = Wwma_Func(src, ma_length) // KAMA Calculation Kama_Func(src, ma_length) => xvnoise = math.abs(src - src[1]) nfastend = 0.666 nslowend = 0.0645 nsignal = math.abs(src - src[ma_length]) nnoise = math.sum(xvnoise, ma_length) nefratio = nnoise != 0 ? nsignal / nnoise : 0 nsmooth = math.pow(nefratio * (nfastend - nslowend) + nslowend, 2) nAMA = 0.0 nAMA := nz(nAMA[1]) + nsmooth * (src - nz(nAMA[1])) nAMA Zlema_Func(src, ma_length) => zxLag = ma_length / 2 == math.round(ma_length / 2) ? ma_length / 2 : (ma_length - 1) / 2 zxEMAData = src + src - src[zxLag] ZLEMA = ta.ema(zxEMAData, ma_length) ZLEMA ZLEMA = Zlema_Func(src, ma_length) Tsf_Func(src, ma_length) => lrc = ta.linreg(src, ma_length, 0) lrc1 = ta.linreg(src, ma_length, 1) lrs = lrc - lrc1 TSF = ta.linreg(src, ma_length, 0) + lrs TSF TSF = Tsf_Func(src, ma_length) HMA = ta.wma(2 * ta.wma(src, ma_length / 2) - ta.wma(src, ma_length), math.round(math.sqrt(ma_length))) T3e1 = ta.ema(src, ma_length) T3e2 = ta.ema(T3e1, ma_length) T3e3 = ta.ema(T3e2, ma_length) T3e4 = ta.ema(T3e3, ma_length) T3e5 = ta.ema(T3e4, ma_length) T3e6 = ta.ema(T3e5, ma_length) T3c1 = -T3a1 * T3a1 * T3a1 T3c2 = 3 * T3a1 * T3a1 + 3 * T3a1 * T3a1 * T3a1 T3c3 = -6 * T3a1 * T3a1 - 3 * T3a1 - 3 * T3a1 * T3a1 * T3a1 T3c4 = 1 + 3 * T3a1 + T3a1 * T3a1 * T3a1 + 3 * T3a1 * T3a1 T3 = T3c1 * T3e6 + T3c2 * T3e5 + T3c3 * T3e4 + T3c4 * T3e3 getMA(src, ma_length) => ma = 0.0 ma := switch mav 'SMA' => ta.sma(src, ma_length) 'EMA' => ta.ema(src, ma_length) 'WMA' => ta.wma(src, ma_length) 'DEMA' => DEMA 'TMA' => ta.sma(ta.sma(src, math.ceil(ma_length / 2)), math.floor(ma_length / 2) + 1) 'VAR' => VAR 'WWMA' => WWMA 'ZLEMA' => ZLEMA 'TSF' => TSF 'HULL' => HMA 'TILL' => T3 'KAMA' => Kama_Func(src, ma_length) ma ALL = getMA(src, ma_length) exMov = ALL fark = exMov * percent * 0.01 longStop = exMov - fark longStopPrev = nz(longStop[1], longStop) longStop := exMov > longStopPrev ? math.max(longStop, longStopPrev) : longStop shortStop = exMov + fark shortStopPrev = nz(shortStop[1], shortStop) shortStop := exMov < shortStopPrev ? math.min(shortStop, shortStopPrev) : shortStop dir = 1 dir := nz(dir[1], dir) dir := dir == -1 and exMov > shortStopPrev ? 1 : dir == 1 and exMov < longStopPrev ? -1 : dir MOST = dir == 1 ? longStop : shortStop cro = _type and _type1 ? ta.crossover(exMov, exMov[1]) : _type ? ta.crossover(close, exMov) : ta.crossover(exMov, MOST) cru = _type and _type1 ? ta.crossunder(exMov, exMov[1]) : _type ? ta.crossunder(close, exMov) : ta.crossunder(exMov, MOST) direction = 0 direction := cro ? 1 : cru ? -1 : direction[1] col1 = exMov > exMov[1] col3 = exMov < exMov[1] colorM = col1 and _type and _type1 ? color.rgb(14, 241, 52) : col3 and _type and _type1 ? color.red : color.new(#00bcd4, 0) if (cro) strategy.entry('LONG', strategy.long) if (cru) strategy.close('LONG') plot(_type ? na : MOST, color=color.new(color.maroon, 0), linewidth=3, title='MOST') plot(exMov, color=colorM, linewidth=2, title='exMov') plotshape(cro and showsignallabels, title='BUY', text='BUY', location=location.belowbar, style=shape.labelup, size=size.tiny, color=color.new(#00bcd4, 0), textcolor=color.new(color.white, 0)) plotshape(cru and showsignallabels, title='SELL', text='SELL', location=location.abovebar, style=shape.labeldown, size=size.tiny, color=color.new(#e91e63, 0), textcolor=color.new(color.white, 0))