Diese Strategie verwendet zwei gleitende Durchschnitte mit unterschiedlichen Parameter-Einstellungen für Crossover-Operationen, um die Trendrichtung und offene/schließende Positionen zu bestimmen. Die Strategie ermöglicht die Auswahl aus 9 verschiedenen Arten von gleitenden Durchschnitten, einschließlich einfacher gleitender Durchschnitte (SMA), exponentieller gleitender Durchschnitte (EMA), gewichteter gleitender Durchschnitte (WMA), Arnaud Legoux gleitender Durchschnitte (ALMA), Volumengewichteter gleitender Durchschnitte (VWMA) usw. Die Strategie setzt auch Stop-Loss- und Take-Profit-Level.
Die Kernlogik dieser Strategie besteht darin, die Werte von zwei gleitenden Durchschnittslinien zu vergleichen und die Markttrendrichtung auf der Grundlage ihrer Überschneidung zu bestimmen. Insbesondere setzen wir eine schnelle Linie und eine langsame Linie mit zwei gleitenden Durchschnitten fest. Wenn die schnelle Linie über die langsame Linie geht, glauben wir, dass der Markt in einem Aufwärtstrend ist und lang geht. Wenn die schnelle Linie unter der langsamen Linie geht, glauben wir, dass der Markt in einem Abwärtstrend ist und kurz geht.
Wenn der Preis die Stop-Loss-Linie berührt, verlassen wir die Position, um Verluste zu reduzieren. Wenn der Preis die Take-Profit-Linie berührt, verlassen wir die Position, um Gewinn zu erzielen, wie erwartet.
Aus der Code-Logik kann die Strategie in vier Teile unterteilt werden:
Berechnen Sie die gleitenden Durchschnitte.Basierend auf der vom Benutzer gewählten Art des gleitenden Durchschnitts berechnen Sie die gleitenden Durchschnitte der schnellen und der langsamen Linie.
Erzeugen Sie lange und kurze Signale, basierend auf den Überschreitungen der schnellen und der langsamen Linie.
Setzen Sie Stop-Loss- und Take-Profit-Levels.
Eintritt und Ausstieg: Eintritt basierend auf den Long/Short-Signalen, Ausstieg basierend auf den Stop Loss/Take Profit-Signalen.
Der größte Vorteil dieser Strategie besteht darin, dass Sie frei aus vielen Arten von gleitenden Durchschnitten wählen können. Verschiedene Arten von gleitenden Durchschnitten haben unterschiedliche Empfindlichkeiten für die Preise. Benutzer können den geeigneten gleitenden Durchschnitt basierend auf ihren eigenen Bedürfnissen auswählen. Darüber hinaus kann die Länge der gleitenden Durchschnitte angepasst werden, um die Zeitdimension zu optimieren.
Ein weiterer Vorteil ist, dass Stop-Loss- und Take-Profit-Mechanismen eingerichtet sind. Dies kann weitere Verluste effektiv verhindern und Gewinne einfangen. Insgesamt ist diese Strategie ziemlich flexibel mit hoher Anpassbarkeit und eignet sich für Benutzer mit unterschiedlichen Bedürfnissen.
Das Hauptrisiko dieser Strategie besteht darin, dass gleitende Durchschnitte zurückbleiben. Wenn die Preise plötzlich heftig schwanken, können gleitende Durchschnitte nicht rechtzeitig reagieren, was dazu führen kann, dass die beste Ein- oder Ausstiegszeit verpasst wird. Dies kann zu großen Verlusten führen.
Ein weiteres Risiko ist die Einstellung von Stop-Loss- und Take-Profit-Niveaus. Wenn der Bereich zu klein ist, kann er für Scalper anfällig sein. Wenn er zu groß ist, ist es leicht, nicht rechtzeitig Gewinne zu erzielen. Daher müssen Stop-Loss-/Take-Profit-Parameter entsprechend den Marktbedingungen während des Live-Handels optimiert werden.
Im Allgemeinen beruht diese Strategie hauptsächlich auf gleitenden Durchschnitten, um die Trendrichtung zu bestimmen. Daher kann ihre Wirksamkeit beeinträchtigt werden, wenn plötzliche Ereignisse zu großen Kursschwankungen führen. Darüber hinaus können Parameter-Einstellungen auch einen großen Einfluss auf die Strategierenditen haben.
Diese Strategie kann in folgenden Aspekten optimiert werden:
Optimieren Sie die Art des gleitenden Durchschnitts. Wählen Sie geeignete gleitende Durchschnitte anhand verschiedener Marktumgebungen und Handelsprodukte aus.
Optimierung der gleitenden Durchschnittsparameter und Anpassung der gleitenden Durchschnittslänge, um sie besser an die Merkmale des Marktes anzupassen.
MACD, RSI und andere Indikatoren können hinzugefügt werden, um häufigen Handel zu vermeiden, wenn kein klarer Trend vorliegt.
Optimieren Sie die Stop-Loss-/Take-Profit-Verhältnisse. Berechnen Sie die optimalen Stop-Loss-/Take-Profit-Parameter anhand historischer Daten.
Fügen Sie maschinelle Lernmodelle hinzu. Verwenden Sie LSTM, zufällige Waldalgorithmen, um Preisbewegungen vorherzusagen und bei der Erzeugung von Handelssignalen zu helfen.
Die Stop-Loss-Linie soll sich allmählich mit den Kursbewegungen bewegen, um die Wahrscheinlichkeit zu verringern, getroffen zu werden.
Insgesamt ist diese Strategie relativ einfach und unkompliziert. Sie bestimmt die Trendrichtung über Crossover und gehört zu einer typischen Trendfolgestrategie. Die Vorteile sind leicht zu verstehen und sehr flexibel mit anpassbaren gleitenden Durchschnittsarten und Parametern. Die Nachteile sind langsamere Reaktionen auf plötzliche Ereignisse und ein gewisses Maß an Verzögerung. Im Allgemeinen eignet sich diese Strategie für Anleger, die langfristige stetige Renditen suchen.
/*backtest start: 2022-12-26 00:00:00 end: 2024-01-01 00:00:00 period: 1d basePeriod: 1h exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}] */ //@version=3 strategy("Kozlod - Yet Another Moving Average Cross Strategy", shorttitle="kozlod_yamacs", overlay = true) // // author: Kozlod // date: 2018-03-06 // //////////// // INPUTS // //////////// ma_type = input(title = "MA Type", defval = "SMA", options = ['SMA', 'EMA', 'WMA', 'ALMA', 'VWMA', 'HMA', 'LSMA', 'SMMA', 'DEMA']) short_ma_len = input(title = "Short MA Length", defval = 5, minval = 1) short_ma_src = input(title = "Short MA Source", defval = close) long_ma_len = input(title = "Long MA Length", defval = 15, minval = 2) long_ma_src = input(title = "Long MA Source", defval = close) alma_offset = input(title = "ALMA Offset", type = float, defval = 0.85, step = 0.01, minval = 0, maxval = 1) alma_sigma = input(title = "ALMA Sigma", type = float, defval = 6, step = 0.01) lsma_offset = input(title = "LSMA Offset", defval = 0, step = 1) sl_lev_perc = input(title = "SL Level % (0 - Off)", type = float, defval = 0, minval = 0, step = 0.01) pt_lev_perc = input(title = "PT Level % (0 - Off)", type = float, defval = 0, minval = 0, step = 0.01) // Set initial values to 0 short_ma = 0.0 long_ma = 0.0 // Simple Moving Average (SMA) if ma_type == 'SMA' short_ma := sma(short_ma_src, short_ma_len) long_ma := sma(long_ma_src, long_ma_len) // Exponential Moving Average (EMA) if ma_type == 'EMA' short_ma := ema(short_ma_src, short_ma_len) long_ma := ema(long_ma_src, long_ma_len) // Weighted Moving Average (WMA) if ma_type == 'WMA' short_ma := wma(short_ma_src, short_ma_len) long_ma := wma(long_ma_src, long_ma_len) // Arnaud Legoux Moving Average (ALMA) if ma_type == 'ALMA' short_ma := alma(short_ma_src, short_ma_len, alma_offset, alma_sigma) long_ma := alma(long_ma_src, long_ma_len, alma_offset, alma_sigma) // Hull Moving Average (HMA) if ma_type == 'HMA' short_ma := wma(2*wma(short_ma_src, short_ma_len/2)-wma(short_ma_src, short_ma_len), round(sqrt(short_ma_len))) long_ma := wma(2*wma(long_ma_src, long_ma_len /2)-wma(long_ma_src, long_ma_len), round(sqrt(long_ma_len))) // Volume-weighted Moving Average (VWMA) if ma_type == 'VWMA' short_ma := vwma(short_ma_src, short_ma_len) long_ma := vwma(long_ma_src, long_ma_len) // Least Square Moving Average (LSMA) if ma_type == 'LSMA' short_ma := linreg(short_ma_src, short_ma_len, lsma_offset) long_ma := linreg(long_ma_src, long_ma_len, lsma_offset) // Smoothed Moving Average (SMMA) if ma_type == 'SMMA' short_ma := na(short_ma[1]) ? sma(short_ma_src, short_ma_len) : (short_ma[1] * (short_ma_len - 1) + short_ma_src) / short_ma_len long_ma := na(long_ma[1]) ? sma(long_ma_src, long_ma_len) : (long_ma[1] * (long_ma_len - 1) + long_ma_src) / long_ma_len // Double Exponential Moving Average (DEMA) if ma_type == 'DEMA' e1_short = ema(short_ma_src, short_ma_len) e1_long = ema(long_ma_src, long_ma_len) short_ma := 2 * e1_short - ema(e1_short, short_ma_len) long_ma := 2 * e1_long - ema(e1_long, long_ma_len) ///////////// // SIGNALS // ///////////// long_signal = crossover( short_ma, long_ma) short_signal = crossunder(short_ma, long_ma) // Calculate PT/SL levels // Initial values last_signal = 0 prev_tr_price = 0.0 pt_level = 0.0 sl_level = 0.0 // Calculate previous trade price prev_tr_price := long_signal[1] or short_signal[1] ? open : nz(last_signal[1]) != 0 ? prev_tr_price[1] : na // Calculate SL/PT levels pt_level := nz(last_signal[1]) == 1 ? prev_tr_price * (1 + pt_lev_perc / 100) : nz(last_signal[1]) == -1 ? prev_tr_price * (1 - pt_lev_perc / 100) : na sl_level := nz(last_signal[1]) == 1 ? prev_tr_price * (1 - sl_lev_perc / 100) : nz(last_signal[1]) == -1 ? prev_tr_price * (1 + sl_lev_perc / 100) : na // Calculate if price hit sl/pt long_hit_pt = pt_lev_perc > 0 and nz(last_signal[1]) == 1 and close >= pt_level long_hit_sl = sl_lev_perc > 0 and nz(last_signal[1]) == 1 and close <= sl_level short_hit_pt = pt_lev_perc > 0 and nz(last_signal[1]) == -1 and close <= pt_level short_hit_sl = sl_lev_perc > 0 and nz(last_signal[1]) == -1 and close >= sl_level // What is last active trade? last_signal := long_signal ? 1 : short_signal ? -1 : long_hit_pt or long_hit_sl or short_hit_pt or short_hit_sl ? 0 : nz(last_signal[1]) ////////////// // PLOTTING // ////////////// // Plot MAs plot(short_ma, color = red, linewidth = 2) plot(long_ma, color = green, linewidth = 2) // Plot Levels plotshape(prev_tr_price, style = shape.cross, color = gray, location = location.absolute, size = size.small) plotshape(sl_lev_perc > 0 ? sl_level : na, style = shape.cross, color = red, location = location.absolute, size = size.small) plotshape(pt_lev_perc > 0 ? pt_level : na, style = shape.cross, color = green, location = location.absolute, size = size.small) ////////////// // STRATEGY // ////////////// strategy.entry("long", true, when = long_signal) strategy.entry("short", false, when = short_signal) strategy.close("long", when = long_hit_pt or long_hit_sl) strategy.close("short", when = short_hit_pt or short_hit_sl)