Die normale Funktion iMA() arbeitet mit Bars, nicht Ticks.
Da meiner Erfahrung kein großer Unterschied zwischen einem ema und einem sma besteht (wenn der (kleine) Unterschied einen Ergebnis-Unterschied macht, wäre meiner Meinung nach das System nichts wert), würde ich einen ema empfehlen, ist schneller weil viel leichter zu berechnen:
Hier zwei Versionen des ema (nxt=der neue Tick, prv= der noch alte Wert des ema, c=Verzögerungskonstante):
#define ema(nxt,prv,c) (c >= 0.99 ? nxt : (((nxt)-(prv))*(c) +(prv))) double c = 2.0/double(n+1); double emaCalc(const double nxt, const double prv, const double c) { return( (nxt-prv)*c + prv ); }
Die normale Funktion iMA() arbeitet mit Bars, nicht Ticks.
Da meiner Erfahrung kein großer Unterschied zwischen einem ema und einem sma besteht (wenn der (kleine) Unterschied einen Ergebnis-Unterschied macht, wäre meiner Meinung nach das System nichts wert), würde ich einen ema empfehlen, ist schneller weil viel leichter zu berechnen:
Hier zwei Versionen des ema (nxt=der neue Tick, prv= der noch alte Wert des ema, c=Verzögerungskonstante):
Danke für die schnelle Antwort!
Was soll die Verzögerungskonstante bezwecken?
Ich habe hier leider wohl grundlegene Verständnisprobleme:
Beim ersten: "Wenn c>= 0.99 'was macht hier das ?' nxt 'was macht hier das :' ? Diese Zeichen bedeuten in fast jeder Sprache was anderes..
Das zweite verstehe ich wohl nicht, weil ich das mit der VK nicht verstehe..
Spricht was dagegen mit aus den Arraywerten [elements-n] den AVG selbst zu berechnen? Das könnte doch sogar das schnellste sein als noch eine Funktion aufzurufen?
Vielen Dank & Gruß
Danke für die schnelle Antwort!
Was soll die Verzögerungskonstante bezwecken?
Ich habe hier leider wohl grundlegene Verständnisprobleme:
Beim ersten: "Wenn c>= 0.99 'was macht hier das ?' nxt 'was macht hier das :' ? Diese Zeichen bedeuten in fast jeder Sprache was anderes..
Das zweite verstehe ich wohl nicht, weil ich das mit der VK nicht verstehe..
Spricht was dagegen mit aus den Arraywerten [elements-n] den AVG selbst zu berechnen? Das könnte doch sogar das schnellste sein als noch eine Funktion aufzurufen?
Vielen Dank & Gruß
dann gibts noch zu beachten, du bekommst die Echteste nicht, dein Broker sendet x Ticks pro Sekunde maximal, das steht leider nirgends was maximal ist. Aber das hat nix mit den real Ticks zu tun, die es wirklich gibt.
Danke für die schnelle Antwort!
Beim ersten: "Wenn c>= 0.99 'was macht hier das ?' nxt 'was macht hier das :' ? Diese Zeichen bedeuten in fast jeder Sprache was anderes..Spricht was dagegen mit aus den Arraywerten [elements-n] den AVG selbst zu berechnen? Das könnte doch sogar das schnellste sein als noch eine Funktion aufzurufen?
Frage 1: siehe https://www.mql5.com/de/docs/basis/operators/ternary
Frage 2: Da spricht absolut nix dagegen.
Wie du mit Ticks umgehen kannst etwas adaptiert:
//+------------------------------------------------------------------+ //| Ticks.mq5 | //| Copyright 2010, MetaQuotes Software Corp. | //| http://www.mql5.com | //| Original code was found on https://www.mql5.com/de/code/89 | //+------------------------------------------------------------------+ #property copyright "2010, MetaQuotes Software Corp." #property link "http://www.mql5.com" #property version "1.00" #property indicator_separate_window #property indicator_buffers 2 #property indicator_plots 2 //--- plot Bid #property indicator_label1 "Bid" #property indicator_type1 DRAW_LINE #property indicator_color1 clrLime #property indicator_style1 STYLE_SOLID #property indicator_width1 1 //--- plot Ask #property indicator_label2 "Ask" #property indicator_type2 DRAW_LINE #property indicator_color2 clrRed #property indicator_style2 STYLE_SOLID #property indicator_width2 1 //--- input parameters input int points_indent = 10; //--- indicator buffers double BidBuffer[]; double AskBuffer[]; //+------------------------------------------------------------------+ //| Custom indicator deinitialization function | //+------------------------------------------------------------------+ void OnDeinit(const int reason) { Comment(""); } //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ int OnInit() { //--- indicator buffers mapping SetIndexBuffer(0,BidBuffer,INDICATOR_DATA); SetIndexBuffer(1,AskBuffer,INDICATOR_DATA); PlotIndexSetDouble(0,PLOT_EMPTY_VALUE,0); PlotIndexSetDouble(1,PLOT_EMPTY_VALUE,0); return(INIT_SUCCEEDED); } //+------------------------------------------------------------------+ //| Custom indicator iteration function | //+------------------------------------------------------------------+ int OnCalculate (const int rates_total, const int prev_calculated, const int begin, const double& price[]) { static int ticks=0; if(ticks==0) { ArrayInitialize(AskBuffer,0); ArrayInitialize(BidBuffer,0); } setMaxMinPrice(ticks,points_indent); MqlTick last_tick; if(SymbolInfoTick(Symbol(),last_tick)) { BidBuffer[ticks]=last_tick.bid; AskBuffer[ticks]=last_tick.ask; int shift=rates_total-1-ticks; ticks++; BidBuffer[rates_total-1]=last_tick.bid; AskBuffer[rates_total-1]=last_tick.ask; PlotIndexSetInteger(0,PLOT_SHIFT,shift); PlotIndexSetInteger(1,PLOT_SHIFT,shift); Comment("Bid =",last_tick.bid," Ask =",last_tick.ask); } return(rates_total); } //+------------------------------------------------------------------+ //| set Maximum and Minimum for an indicator window based on last values //+------------------------------------------------------------------+ void setMaxMinPrice(int last_values,int indent) { int visiblebars=(int)ChartGetInteger(0,CHART_VISIBLE_BARS); int depth=MathMin(last_values,visiblebars); int startindex=last_values-depth; if(startindex<0) startindex=0; int max_index=ArrayMaximum(AskBuffer,startindex,depth); max_index=max_index>=0?max_index:0; int min_index=ArrayMinimum(BidBuffer,startindex,depth); min_index=min_index>=0?min_index:0; double MaxPrice=AskBuffer[max_index]+indent*_Point; double MinPrice=BidBuffer[min_index]-indent*_Point; IndicatorSetDouble(INDICATOR_MAXIMUM,MaxPrice); IndicatorSetDouble(INDICATOR_MINIMUM,MinPrice); }
Dieser Indi berechnet SMA,EMA,WMA auf tickbasis. Beide Indis sind nur im Tester getestet und reine versuchsindikatoren.
//+------------------------------------------------------------------+ //| Tick_MAs.mq5 | //| Copyright © 2018, Ing. Otto Pauser | //| https://www.mql5.com/de/users/kronenchakra | //+------------------------------------------------------------------+ #property copyright "Copyright © 2018, Ing. Otto Pauser" #property link "https://www.mql5.com/de/users/kronenchakra" #property version "1.00" #property description "Study of MAs on Ticks\n\nTo hide a lines set it's color to NONE" #property indicator_separate_window #define BUFFERS 6 #property indicator_buffers BUFFERS #property indicator_plots BUFFERS //#include <Info.mqh> //#include <HLine.mqh> //+------------------------------------------------------------------+ //| input parameters | //+------------------------------------------------------------------+ input int inpPeriod = 120; // Period input color inpColorAsk = clrRed; // Color Ask input color inpColorMid = clrNONE; // Color Mid input color inpColorBid = clrSteelBlue; // Color Bid input color inpColorSMA = clrLime; // Color SMA input color inpColorEMA = clrAqua; // Color EMA input color inpColorWMA = clrRed; // Color WMA //input bool inpShowInfo = true; // Show Info //input bool inpInfoSubwin = true; // Show Info in subwindow //input bool inpShowBid = true; // Show bid price line //input bool inpShowAsk = true; // Show ask price line int inpLineWidth = 1; // Linewidth //+------------------------------------------------------------------+ double Ask[], Bid[], Mid[], // buffers for rates SMA[], EMA[], WMA[]; // buffers for MAs double slSMA, slEMA, slWMA; // slopes string IndiName = "Tick_MAs"; // indicator shortname //CHLine bidLine, askLine; //+------------------------------------------------------------------+ //| initialization | //+------------------------------------------------------------------+ int OnInit() { Indi.InitLine (Ask,STYLE_SOLID,inpLineWidth,inpColorAsk,"ASK"); Indi.InitLine (Mid,STYLE_DOT ,inpLineWidth,inpColorMid,"MID"); Indi.InitLine (Bid,STYLE_SOLID,inpLineWidth,inpColorBid,"BID"); Indi.InitLine (EMA,STYLE_SOLID,inpLineWidth,inpColorEMA,"EMA("+IntegerToString(inpPeriod)+")"); Indi.InitLine (WMA,STYLE_SOLID,inpLineWidth,inpColorWMA,"WMA("+IntegerToString(inpPeriod)+")"); Indi.InitLine (SMA,STYLE_SOLID,inpLineWidth,inpColorSMA,"SMA("+IntegerToString(inpPeriod)+")"); IndicatorSetString (INDICATOR_SHORTNAME,IndiName); return(INIT_SUCCEEDED); } //+------------------------------------------------------------------+ //| mainloop of indicator | //+------------------------------------------------------------------+ int OnCalculate (const int rates_total, const int prev_calculated, const int begin, const double& price[]) { static int ticks=0; int shift,i; MqlTick last_tick; if(ticks==0) // first call of OnCalculate() { //if(inpInfoSubwin) // not possible in OnInit // Info.SetSubwindow(); if(!MQLInfoInteger(MQL_TESTER)) // does not work in tester ticks=LoadTicks(Ask,Mid,Bid); // load ticks from cache if(ticks<0) return(NULL); // no ticks available for(i=inpPeriod; i<ticks; i++) // calculate the MAs { SMA[i]=iSMA(i,inpPeriod,Mid); EMA[i]=iEMA(i,inpPeriod,Mid); WMA[i]=iWMA(i,inpPeriod,Mid); //shift=rates_total-1-ticks; // calculate shift of buffers //for(i=0; i<BUFFERS; i++) // shift all buffers // PlotIndexSetInteger(i,PLOT_SHIFT,shift); } } if(SymbolInfoTick(Symbol(),last_tick)) // get current tick { Ask[ticks]= last_tick.ask; // copy to buffers Mid[ticks]=(last_tick.ask+last_tick.bid)*0.5; Bid[ticks]= last_tick.bid; // calculate the MAs if(ticks>inpPeriod) { SMA[ticks]=iSMA(ticks,inpPeriod,Mid); EMA[ticks]=iEMA(ticks,inpPeriod,Mid); WMA[ticks]=iWMA(ticks,inpPeriod,Mid); slSMA=(SMA[ticks]-SMA[ticks-1])/_Point; slEMA=(EMA[ticks]-EMA[ticks-1])/_Point; slWMA=(WMA[ticks]-WMA[ticks-1])/_Point; } shift=rates_total-1-ticks; // calculate shift of buffers for(i=0; i<BUFFERS; i++) // shift all buffers PlotIndexSetInteger(i,PLOT_SHIFT,shift); //if(inpShowAsk) askLine.Draw("Ask",last_tick.ask,inpColorAsk,1,STYLE_DASHDOT,IndiName); //if(inpShowBid) bidLine.Draw("Bid",last_tick.bid,inpColorBid,1,STYLE_DASHDOT,IndiName); // if(inpShowInfo) // { // Info.Info( "Symbol :",_Symbol); // Info.Info("Slope SMA :",slSMA); // Info.Info("Slope EMA :",slEMA); // Info.Info("Slope WMA :",slWMA); // Info.Info( "Spread :",SymbolInfoInteger(_Symbol,SYMBOL_SPREAD)); // Info.Info( "Shift :",shift); // // //Info.Info( "Ask :",last_tick.ask); // //Info.Info( "Bid :",last_tick.bid); // //Info.Info( "Swap Long :",SymbolInfoDouble (_Symbol,SYMBOL_SWAP_LONG ),2); // //Info.Info("Swap Short :",SymbolInfoDouble (_Symbol,SYMBOL_SWAP_SHORT),2); // } ticks++; // increment tick counter } return(rates_total); // return rates_total for next call of OnCalculate() } //+------------------------------------------------------------------+ //| calculate EMA | //+------------------------------------------------------------------+ double iEMA(const int position,const int period, const double &price[]) { static bool first=true; static double prev_value; if(first) { first=false; prev_value=price[position]; return(prev_value); } double result=0.0; if(period>0) { double pr=2.0/(period+1.0); result=price[position]*pr+prev_value*(1-pr); } prev_value=result; return(result); } //+------------------------------------------------------------------+ //| calculate SMA | //+------------------------------------------------------------------+ double iSMA(const int position,const int period, const double &buffer[]) { int i; static double sum=NULL; if(sum==NULL) { if(position>=period-1 && period>0) { for(i=period; i>0 ;i--) sum+=buffer[position-i+1]; } } sum=sum+(buffer[position]-buffer[position-period]); return(sum/period); } //+------------------------------------------------------------------+ //| calculate LWMA | //+------------------------------------------------------------------+ double iWMA(const int position,const int period,const double &price[]) { double result=0.0,sum=0.0; int i,wsum=0; if(position>=period-1 && period>0) { for(i=period; i>0 ;i--) { wsum+=i; sum+=price[position-i+1]*(period-i+1); } result=sum/wsum; } return(result); } //+------------------------------------------------------------------+ //| load tickdata from cache | //+------------------------------------------------------------------+ int LoadTicks(double &askBuf[], double &midBuf[], double &bidBuf[]) { MqlTick TickArray[]; // array of ticks int loaded=CopyTicks(_Symbol,TickArray); // load ticks from cache for(int i=0; i<loaded; i++) // copy ticks to buffers { askBuf[i]= TickArray[i].ask; midBuf[i]=(TickArray[i].ask+TickArray[i].bid)*0.5; bidBuf[i]= TickArray[i].bid; } return(loaded); // return number of ticks loaded } //+------------------------------------------------------------------+ //| define a class for easy and cmfortable buffer definition | //+------------------------------------------------------------------+ class CIndi { private: int m_BufIdx; // counter for bufferindex public: bool InitLine (double &aBuffer[], // the buffer ENUM_LINE_STYLE aLineStyle=STYLE_SOLID, // STYLE_SOLID .. STYLE_DASHDOTDOT int aLineWidth=1, // PLOT_LINE_WIDTH int aLineColor=clrRed, // PLOT_LINE_COLOR string aPlotLabel="") // PLOT_LABEL - "Any String" { SetIndexBuffer (m_BufIdx,aBuffer, INDICATOR_DATA); PlotIndexSetInteger(m_BufIdx,PLOT_DRAW_TYPE, DRAW_LINE); PlotIndexSetInteger(m_BufIdx,PLOT_LINE_STYLE, aLineStyle); PlotIndexSetInteger(m_BufIdx,PLOT_LINE_WIDTH, aLineWidth); PlotIndexSetInteger(m_BufIdx,PLOT_LINE_COLOR, aLineColor); PlotIndexSetString (m_BufIdx,PLOT_LABEL, aPlotLabel); PlotIndexSetDouble (m_BufIdx,PLOT_EMPTY_VALUE,NULL); ArrayInitialize (aBuffer,NULL); // initialize arrays m_BufIdx++; // increment bufferindex for next Init() return(true); } }; CIndi Indi; // instance of CIndi
Da hab ich ziemlich 'herumgewütet' weil CopyTicks() im Tester nicht funktioniert, hat es aber früher, oder ich bilde es mir blos ein.
![Dokumentation zu MQL5: Grundlagen der Sprache / Operatoren / Ternärer Operator ?: Dokumentation zu MQL5: Grundlagen der Sprache / Operatoren / Ternärer Operator ?:](https://c.mql5.com/36/30/dokumentation-zu-mql5-grundlagen.png)
- www.mql5.com
Frage 1: siehe https://www.mql5.com/de/docs/basis/operators/ternary
Frage 2: Da spricht absolut nix dagegen.
Wie du mit Ticks umgehen kannst etwas adaptiert:
Dieser Indi berechnet SMA,EMA,WMA auf tickbasis. Beide Indis sind nur im Tester getestet und reine versuchsindikatoren.
Da hab ich ziemlich 'herumgewütet' weil CopyTicks() im Tester nicht funktioniert, hat es aber früher, oder ich bilde es mir blos ein.
Danke Otto, ist ja interessant mit dem ? :.. immer das selbe in einer anderen Form.. danke für den Link und Deinen Code, den ich mir morgen etwas länger ansehen werde.
Bei mir im Tester funktioniert CopyTicks; also zumindest sehe ich im Array, in das ich kopiere, alle Werte.. bzw. last, volume und volume_real sind leider stets 0.000.
VG
dann gibts noch zu beachten, du bekommst die Echteste nicht, dein Broker sendet x Ticks pro Sekunde maximal, das steht leider nirgends was maximal ist. Aber das hat nix mit den real Ticks zu tun, die es wirklich gibt.
Ja, habe ich schon in einem Artikel hier gelesen, dass es von Bloomberg eine andere Tickqualität bzw. Menge gibt.. aber was soll man machen? Ich kann mir jetzt nicht für ein paar 1000€/Monat einen Bloomberg-Zugriff kaufen.
QTrade bringt bis 6 Ticks pro Sekunde; ich denke bei ordentlich Momentum bei frischen Wirtschaftsdaten noch mehr; damit muss ich erstmal arbeiten. Oder hast Du, von enormen Investitionen abgesehen, eine Alternative?
VG
![MQL5 - Sprache von Handelsstrategien, eingebaut ins Kundenterminal MetaTrader 5](https://c.mql5.com/i/registerlandings/logo-2.png)
- Freie Handelsapplikationen
- Über 8.000 Signale zum Kopieren
- Wirtschaftsnachrichten für die Lage an den Finanzmärkte
Sie stimmen der Website-Richtlinie und den Nutzungsbedingungen zu.
Hallo,
ich gestehe, dass ich noch nicht in die i(average)Funktionen eingetaucht bin, da ich nicht weiß, ob ich sie in meinen nächsten Schritten anwenden werde; ich finde das Thema auch nicht ganz so einfach.
Kann ich eine dieser Funktion nutzen, um an den Durchschnitt der letzten 5,10 und 100 Ticks zu kommen? Wenn ja, welche sollte ich mir da ansehen?
Oder muss ich den Durchschnitt der letzten Ticks zu Fuß rechnen?
1000 Dank & VG,
Christian