Multi-Time Frame MA Mondrian Crossover Strategie


Erstellungsdatum: 2023-11-16 17:28:43 zuletzt geändert: 2023-11-16 17:28:43
Kopie: 0 Klicks: 661
1
konzentrieren Sie sich auf
1617
Anhänger

Multi-Time Frame MA Mondrian Crossover Strategie

Die Strategie verwendet hauptsächlich die Kreuzung der MA-Linien der Multiple Time Frame (MTF) zur Bestimmung der Trendrichtung und kombiniert mit bestimmten bedingten Filtersignalen, die bei einer klaren Trendrichtung zu kaufen oder zu verkaufen sind. Sie gehört zu den Strategien des Trendverfolgungstyps.

Strategieprinzip

  1. Geben Sie den benutzerdefinierten Messzeitraum ein.

  2. Einzug in die Heikin-Ashi-Karte mit der Synthese von Y und Y, die standardmäßig verwendet wird.

  3. Definition der langsamen MA-Linie, der schnellen MA-Linie und der optional dritten MA-Linie, die bei der Erschütterung verwendet wird.

  4. Für jede MA-Linie können der MA-Typ, die Zeitspanne und die Parameter angepasst werden.

  5. Aufgrund des schnellen MA bildet sich ein Kaufsignal, das durch den langsamen MA über dem schnellen MA überschritten wird.

  6. Optional kann die dritte MA-Leitung als Mehrspur-Filter verwendet werden, um ein Kaufsignal nur zu erzeugen, wenn der Schlusskurs über der dritten MA liegt.

  7. Die Autohandelsplattform wird mit dem Strategy.entry-Modul betrieben.

  8. Die Anzahl der Transaktionen pro Hand kann angepasst oder mit einem festen Transaktionsvolumen durchgeführt werden.

Strategische Vorteile

  1. Mit der MTF-Architektur können unterschiedliche MA-Linien unterschiedliche Perioden verwenden, um Trendmerkmale auf mehreren Zeitskalen zu erkennen.

  2. Anpassung der MA-Typen, Auswahl der glatten MA zur Steigerung der Stabilität und der MA, die schnell reagiert.

  3. In Kombination mit Heikin-Ashi kann ein falscher Durchbruch gefiltert werden.

  4. Eine dritte MA-Leitung kann zusätzlich als mehrsprachiger Richtungsfilter zur Vermeidung von Schaukelhandel verwendet werden.

  5. Flexible Anpassung der MA-Zyklusparameter an unterschiedliche Marktumgebungen.

  6. Das Strategy.entry Modul ermöglicht automatische Bestellungen ohne manuelle Eingriffe.

  7. Unterstützt die Rückmessung von Optimierungsparametern, um die optimale Kombination von Parametern zu finden.

Strategisches Risiko

  1. MA-Kreuzungsstrategien sind empfindlich für durchbrochene Falschsignale und können zu unnötigen Transaktionen führen. Sie können die MA-Zyklen entsprechend anpassen oder die Filterbedingungen erhöhen, um das Risiko zu verringern.

  2. In schwankenden Zeiten können sich die MA-Linien häufig kreuzen, was zu Verlusten führen kann. Um das Risiko zu verringern, kann die MA-Spanne entsprechend verlängert oder der MA-Zyklus verlängert werden.

  3. Die Risiken können nicht durch ein festes Handelsvolumen kontrolliert werden. Es kann in Betracht gezogen werden, das Handelsvolumen als Prozentsatz des Kontogeldes festzulegen.

  4. Die Kosten für den Handel und die Gleitpunkte beeinflussen auch die Profitabilität der Strategie. Die Parameter können entsprechend angepasst werden, um sicherzustellen, dass die Gewinnrate hoch genug ist.

Optimierungsrichtung

  1. Verschiedene MA-Typen werden getestet, um die optimale Kombination von Parametern zu finden. Smooth MA erhöht die Stabilität, schnelle MA erhöht die Agilität.

  2. Optimierung der MA-Parameter, angemessene Verlängerung der Periode zur Erkennung von Trends, Verkürzung der Periode zur Erhöhung der Empfindlichkeit.

  3. Optimierung der Lageröffnungsbedingungen, Erwägung der Stärkung der Mehrkopf-Filterung und Vermeidung von Lageröffnungen in schwankenden Märkten.

  4. Die MA-Zyklusparameter können für eine bestimmte Sorte optimiert werden, um die Parameter zu finden, die am besten für die Handelsumgebung der Sorte geeignet sind.

  5. Strategische Stabilität kann in Kombination mit anderen Indikatoren als Filter betrachtet werden, wie z. B. dem Volumen-Energie-Indikator.

  6. Optimierung der Parameterkombinationen für die Rückmeldedaten, um die besten Parameter zu finden, um die Effektivität der Strategie zu verbessern.

Zusammenfassen

Die Multi-Time-Frame-MA-Kreuzungsstrategie gehört insgesamt zu den häufigsten Trend-Tracking-Strategien. Ihre Vorteile liegen in der Einfachheit, der Flexibilität der Parameteranpassung und der Anpassung an verschiedene Marktumgebungen. Es besteht jedoch ein gewisses Risiko für Falschsignale.

Strategiequellcode
/*backtest
start: 2023-11-08 00:00:00
end: 2023-11-15 00:00:00
period: 1h
basePeriod: 15m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

//@version=4
strategy(shorttitle="MZ MA Cross",title="MA MTF Cross Strategy", overlay=true, calc_on_order_fills=false, calc_on_every_tick=false, default_qty_type=strategy.fixed, default_qty_value=5,commission_value=0.1)

timeFrameticker  = input('D',type=input.resolution, title="Chart Timeframe")
uha   =input(true, title="Use Heikin Ashi Candles")

// Use only Heikinashi Candles for all calculations
haclose = uha ? security(heikinashi(syminfo.tickerid), timeFrameticker, close) : security(syminfo.tickerid, timeFrameticker, close)
haopen = uha ? security(heikinashi(syminfo.tickerid), timeFrameticker, open) : security(syminfo.tickerid, timeFrameticker, open)
hahigh = uha ? security(heikinashi(syminfo.tickerid), timeFrameticker, high) : security(syminfo.tickerid, timeFrameticker, high)
halow = uha ?security(heikinashi(syminfo.tickerid), timeFrameticker, low) : security(syminfo.tickerid, timeFrameticker, low)

//Backtest dates
fromMonth = input(defval = 1,    title = "From Month",      type = input.integer, minval = 1, maxval = 12)
fromDay   = input(defval = 1,    title = "From Day",        type = input.integer, minval = 1, maxval = 31)
fromYear  = input(defval = 2021, title = "From Year",       type = input.integer, minval = 1970)
thruMonth = input(defval = 12,    title = "Thru Month",      type = input.integer, minval = 1, maxval = 12)
thruDay   = input(defval = 30,    title = "Thru Day",        type = input.integer, minval = 1, maxval = 31)
thruYear  = input(defval = 2021, title = "Thru Year",       type = input.integer, minval = 1970)

showDate  = input(defval = true, title = "Show Date Range", type = input.bool)

start     = timestamp(fromYear, fromMonth, fromDay, 00, 00)        // backtest start window
finish    = timestamp(thruYear, thruMonth, thruDay, 23, 59)        // backtest finish window
window()  => true

src = security(heikinashi(syminfo.tickerid), timeFrameticker, close)

//  INPUT MA TYPE
slowMAtype = input(title="Slow MA Type", type=input.string, defval="LRC", options=["SMA","EMA","DEMA","TEMA","LRC","WMA","MF","VAMA","TMA","HMA", "JMA", "Kijun v2", "EDSMA","McGinley"])
fastMAtype = input(title="Fast MA Type", type=input.string, defval="EDSMA", options=["SMA","EMA","DEMA","TEMA","LRC","WMA","MF","VAMA","TMA","HMA", "JMA", "Kijun v2", "EDSMA","McGinley"])
upMAcond =input(false, title="Use Uptrend Conditional 3rd MA for Confirmation")
upMAtype=input(title="Uptrend Conditional MA Type", type=input.string, defval="HMA", options=["SMA","EMA","DEMA","TEMA","LRC","WMA","MF","VAMA","TMA","HMA", "JMA", "Kijun v2", "EDSMA","McGinley"])


//  INPUT RESOLUTION
slowMAresolution = input("D",type=input.resolution, title="Slow MA Resolution")
fastMAresolution = input("D",type=input.resolution, title="Fast MA Resolution")
upMAresolution = input("D",type=input.resolution, title="Uptrend Conditional MA Resolution")
haMAslow = uha ? security(heikinashi(syminfo.tickerid), slowMAresolution, close) : security(syminfo.tickerid, slowMAresolution, close)
haMAfast = uha ?security(heikinashi(syminfo.tickerid), fastMAresolution, close) : security(syminfo.tickerid, fastMAresolution, close)
haMAup =  uha ?security(heikinashi(syminfo.tickerid), upMAresolution, close) : security(syminfo.tickerid, upMAresolution, close)

//  INPUT LENGTHS
slowMAlength = input(50, minval=1, title="Slow MA Length")
fastMAlength = input(30, minval=1, title="Fast MA Length")
upMAlength =  input(200, minval=1, title="Uptrend Conditional MA Length")

/////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////
/////                      MA Function                         //////
/////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////

//           Pre-reqs
//
tema(src, len) =>
    ema1 = ema(src, len)
    ema2 = ema(ema1, len)
    ema3 = ema(ema2, len)
    (3 * ema1) - (3 * ema2) + ema3
kidiv = input(defval=1,maxval=4,  title="Kijun MOD Divider")

jurik_phase = input(title="* Jurik (JMA) Only - Phase", type=input.integer, defval=3)
jurik_power = input(title="* Jurik (JMA) Only - Power", type=input.integer, defval=1)
volatility_lookback = input(10, title="* Volatility Adjusted (VAMA) Only - Volatility lookback length")
//                  MF
beta = input(0.8,minval=0,maxval=1,step=0.1,  title="Modular Filter, General Filter Only - Beta")
feedback = input(false, title="Modular Filter Only - Feedback")
z = input(0.5,title="Modular Filter Only - Feedback Weighting",step=0.1, minval=0, maxval=1)
//EDSMA
ssfLength = input(title="EDSMA - Super Smoother Filter Length", type=input.integer, minval=1, defval=20)
ssfPoles = input(title="EDSMA - Super Smoother Filter Poles", type=input.integer, defval=2, options=[2, 3])

//----
//                  EDSMA
get2PoleSSF(src, length) =>
    PI = 2 * asin(1)
    arg = sqrt(2) * PI / length
    a1 = exp(-arg)
    b1 = 2 * a1 * cos(arg)
    c2 = b1
    c3 = -pow(a1, 2)
    c1 = 1 - c2 - c3
    
    ssf = 0.0
    ssf := c1 * src + c2 * nz(ssf[1]) + c3 * nz(ssf[2])

get3PoleSSF(src, length) =>
    PI = 2 * asin(1)

    arg = PI / length
    a1 = exp(-arg)
    b1 = 2 * a1 * cos(1.738 * arg)
    c1 = pow(a1, 2)

    coef2 = b1 + c1
    coef3 = -(c1 + b1 * c1)
    coef4 = pow(c1, 2)
    coef1 = 1 - coef2 - coef3 - coef4

    ssf = 0.0
    ssf := coef1 * src + coef2 * nz(ssf[1]) + coef3 * nz(ssf[2]) + coef4 * nz(ssf[3])

//          MA Main function
ma(type, src, len) =>
    float result = 0
    if type=="TMA"
        result := sma(sma(src, ceil(len / 2)), floor(len / 2) + 1)
    if type=="MF"
        ts=0.,b=0.,c=0.,os=0.
        //----
        alpha = 2/(len+1)
        a = feedback ? z*src + (1-z)*nz(ts[1],src) : src
        //----
        b := a > alpha*a+(1-alpha)*nz(b[1],a) ? a : alpha*a+(1-alpha)*nz(b[1],a)
        c := a < alpha*a+(1-alpha)*nz(c[1],a) ? a : alpha*a+(1-alpha)*nz(c[1],a)
        os := a == b ? 1 : a == c ? 0 : os[1]
        //----
        upper = beta*b+(1-beta)*c
        lower = beta*c+(1-beta)*b 
        ts := os*upper+(1-os)*lower
        result := ts
    if type=="LRC"
        result := linreg(src, len, 0)
    if type=="SMA" // Simple
        result := sma(src, len)
    if type=="EMA" // Exponential
        result := ema(src, len)
    if type=="DEMA" // Double Exponential
        e = ema(src, len)
        result := 2 * e - ema(e, len)
    if type=="TEMA" // Triple Exponential
        e = ema(src, len)
        result := 3 * (e - ema(e, len)) + ema(ema(e, len), len)
    if type=="WMA" // Weighted
        result := wma(src, len)
    if type=="VAMA" // Volatility Adjusted
        /// Copyright © 2019 to present, Joris Duyck (JD)
        mid=ema(src,len)
        dev=src-mid
        vol_up=highest(dev,volatility_lookback)
        vol_down=lowest(dev,volatility_lookback)
        result := mid+avg(vol_up,vol_down)
    if type=="HMA" // Hull
        result := wma(2 * wma(src, len / 2) - wma(src, len), round(sqrt(len)))
    if type=="JMA" // Jurik
        /// Copyright © 2018 Alex Orekhov (everget)
        /// Copyright © 2017 Jurik Research and Consulting.
        phaseRatio = jurik_phase < -100 ? 0.5 : jurik_phase > 100 ? 2.5 : jurik_phase / 100 + 1.5
        beta = 0.45 * (len - 1) / (0.45 * (len - 1) + 2)
        alpha = pow(beta, jurik_power)
        jma = 0.0
        e0 = 0.0
        e0 := (1 - alpha) * src + alpha * nz(e0[1])
        e1 = 0.0
        e1 := (src - e0) * (1 - beta) + beta * nz(e1[1])
        e2 = 0.0
        e2 := (e0 + phaseRatio * e1 - nz(jma[1])) * pow(1 - alpha, 2) + pow(alpha, 2) * nz(e2[1])
        jma := e2 + nz(jma[1])
        result := jma
    if type=="Kijun v2"
        kijun = avg(lowest(len), highest(len))//, (open + close)/2)
        conversionLine = avg(lowest(len/kidiv), highest(len/kidiv))
        delta = (kijun + conversionLine)/2
        result :=delta
    if type=="McGinley"
        mg = 0.0
        mg := na(mg[1]) ? ema(src, len) : mg[1] + (src - mg[1]) / (len * pow(src/mg[1], 4))
        result :=mg
    if type=="EDSMA"
    
        zeros = src - nz(src[2])
        avgZeros = (zeros + zeros[1]) / 2
        
        // Ehlers Super Smoother Filter 
        ssf = ssfPoles == 2
             ? get2PoleSSF(avgZeros, ssfLength)
             : get3PoleSSF(avgZeros, ssfLength)
        
        // Rescale filter in terms of Standard Deviations
        stdev = stdev(ssf, len)
        scaledFilter = stdev != 0
             ? ssf / stdev
             : 0
        
        alpha = 5 * abs(scaledFilter) / len
        
        edsma = 0.0
        edsma := alpha * src + (1 - alpha) * nz(edsma[1])
        result :=  edsma
    result
/////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////


//  MA DEFINITION
slowMA = ma(slowMAtype, haMAslow , slowMAlength)
//fastMA = ma(fastMAtype, slowMA , fastMAlength)
fastMA = ma(fastMAtype, haMAfast , fastMAlength)
upMA = ma(upMAtype, haMAup , upMAlength)
closeMA = ma('SMA', src , 2)

//  Strategy Conditions
L1 = crossover(fastMA,slowMA)
L2 = close > upMA
S1 = crossunder(fastMA,slowMA)
S2 = close < upMA
longcondition = upMAcond ? L1 and L2 : L1
shortcondition = upMAcond ? S1 or S2 : S1

//  Plots
color_fill_uptrend = color.new(#4caf50, 80)
color_fill_downtrend = color.new(#c2185b, 80)
plot(slowMA, title='Slow MA', color=color.olive, linewidth=2)
plot(fastMA, title='Fast MA', color=color.teal, linewidth=2)
cls=plot(closeMA, title='Source Line', color=na, linewidth=1)
up = plot(upMA, title='Uptrend Conditional MA', color=color.purple, linewidth=2)
fill(up,cls, color = close > upMA ? color_fill_uptrend : color_fill_downtrend )

//plotshape(longcondition, style = shape.triangleup, color = color.green, location = location.belowbar, text = "Long", size = size.small)
//plotshape(shortcondition, style = shape.triangledown, color = color.red, location = location.abovebar, text = "Short", size = size.small)


strategy.entry(id="long", long = true, when = longcondition and window())
strategy.close("long", when = shortcondition and window())

//if (longcondition)
//    strategy.entry("BUY", strategy.long, when = window())

//if (shortcondition)
//    strategy.entry("SELL", strategy.short, when = window())