Diskussion zum Artikel "Was ist ein Trend und basiert die Marktstruktur auf einem Trend oder einer Seitwärtsbewegung?" - Seite 10

 

Ich verstehe, was Ihr Problem war. Zu Beginn sagen Sie, dass der Prozess eine maximale Abweichung von 40 haben kann, und Sie rechnen mit 40. Aber der Prozess hat die Möglichkeit, sowohl in + als auch in - zu gehen, was zu 81 Varianten führt (mit einer genauen 0).

Auf der X-Achse werden 40 Punkte in 2er-Schritten geclustert.

Deshalb haben Sie ein solches Diagramm.

Ich habe die Daten von Excel nach MQL übertragen.

Und mit Hilfe der Funktionen der Standardbibliothek habe ich Sigma-Parameter ausgewählt, um Ihr Diagramm aus Excel zu wiederholen und ebenfalls zwangsweise mit Schritt 2 zu gruppieren.

Es stellt sich heraus, dass für Ihren Prozess mit Kombinatorik der Prozess mit einer Normalverteilung von MO 0 und Sigma 6,45 geeignet ist.

//+------------------------------------------------------------------+
//|NormalSimple.mq5 |
//|https://www.mql5.com |
//+------------------------------------------------------------------+
#include <Graphics\Graphic.mqh>
#include <Math\Stat\Normal.mqh>
#include <Math\Stat\Math.mqh>
#property script_show_inputs
//--- Eingabeparameter
input double mean_value=0;  // Mathematische Erwartung (Mittelwert)
input double std_dev=6.45;     // Standardabweichung (Standardabweichung)
//+------------------------------------------------------------------+
//| Skript-Programmstartfunktion|
//+------------------------------------------------------------------+
void OnStart()
  {
   double arrayTeoryX[41]= {-40,-38,-36,-34,-32,-30,-28,-26,-24,-22,-20,-18,-16,-14,-12,-10,-8,-6,-4,-2,0,
                            2,4,6,8,10,12,14,16,18,20,22,24,26,28,30,32,34,36,38,40
                           };
   double arrayTeoryY[41]= {0.00000009,3.63798 E-06,7.09406 E-05,0.000898581,0.008311872,0.059845479,0.349098627,
                            1.695621904,6.994440355,24.86912126,77.09427591,210.2571161,508.121364,1094.415245,
                            2110.657973,3658.473821,5716.365345,8070.162839,10311.87474,11940.06549,12537.06876,
                            11940.06549,10311.87474,8070.162839,5716.365345,3658.473821,2110.657973,1094.415245,
                            508.121364,210.2571161,77.09427591,24.86912126,6.994440355,1.695621904,0.349098627,
                            0.059845479,0.008311872,0.000898581,7.09406 E-05,3.63798 E-06,9.09495 E-08
                           };
//--- Anzeige des Preisdiagramms deaktivieren
   ChartSetInteger(0,CHART_SHOW,false);
//--- Initialisierung des Zufallszahlengenerators
   MathSrand(GetTickCount());
//--- Erzeugen einer Stichprobe der Zufallsvariablen
   long chart=0;
   string name="GraphicNormal";
   int n=100000;       // Anzahl der Werte in der Stichprobe
   int ncells=41;       // Anzahl der Intervalle im Histogramm
   double x[];          // Histogramm-Intervallzentren
   double y[];          // Anzahl der Werte aus der Stichprobe, die in das Intervall fallen
   double data[];       // Stichprobe von Zufallswerten
   double max,min;      // Höchst- und Mindestwerte in der Stichprobe
//--- eine Stichprobe aus der Normalverteilung erhalten
   MathRandomNormal(mean_value,std_dev,n,data);
//--- Daten für die Erstellung von Histogrammen berechnen
   CalculateHistogramArray(data,x,y,max,min,ncells);
   /*
//--- Sequenzgrenzen und Schritt für theoretische Kurvenkonstruktion ermitteln
 double step;
 GetMaxMinStepValues(max,min,step);
 step=MathMin(step,(max-min)/ncells);
//--- theoretisch berechnete Daten auf dem Intervall [min,max] ermitteln
 double x2[];
 double y2[];
 MathSequence(min,max,step,x2);
 MathProbabilityDensityNormal(x2,mean_value,std_dev,false,y2);
//--- Skalierung
 double theor_max=y2[ArrayMaximum(y2)];
 double sample_max=y[ArrayMaximum(y)];
 double k=sample_max/theor_max;
 */
   /*
 for(int i=0; i<ncells; i++)
 y[i]/=k;
 */
//--- Diagramme anzeigen
   CGraphic graphic;
   if(ObjectFind(chart,name)<0)
      graphic.Create(chart,name,0,0,0,1000,680);
   else
      graphic.Attach(chart,name);
   graphic.BackgroundMain(StringFormat("Normal distribution mu=%G sigma=%G",mean_value,std_dev));
   graphic.BackgroundMainSize(16);
//--- alle Kurven zeichnen
   graphic.CurveAdd(x,y,CURVE_HISTOGRAM,"MQL step 2").HistogramWidth(6);
   graphic.CurveAdd(arrayTeoryX,arrayTeoryY,CURVE_LINES,"Excel");
//--- und nun zeichnen wir die theoretische Verteilungsdichtekurve
//graphic.CurveAdd(x2,y2,CURVE_LINES, "Theorie");
//--- alle Kurven zeichnen
   graphic.CurvePlotAll();
   graphic.Update();
   double summ=0;
   for(int i=0; i<ArraySize(y); i++)
     {
      summ+=y[i];
     }
   Print("Gesamtbetrag bis Y" + summ);
  }
//+------------------------------------------------------------------+
//| Häufigkeiten für den Datensatz berechnen|
//+------------------------------------------------------------------+
bool CalculateHistogramArray(const double &data[],double &intervals[],double &frequency[],
                             double &maxv,double &minv,const int cells=10)
  {
   if(cells<=1)
      return (false);
   int size=ArraySize(data);
   if(size<cells*10)
      return (false);
   minv=data[ArrayMinimum(data)];
   maxv=data[ArrayMaximum(data)];
   double range=maxv-minv;
   double width=range/cells;
   width=2.0;
   minv=-41;
   if(width==0)
      return false;
   ArrayResize(intervals,cells);
   ArrayResize(frequency,cells);
//--- die Zentren der Intervalle festlegen
   for(int i=0; i<cells; i++)
     {
      intervals[i]=minv+(i+0.5)*width;
      frequency[i]=0;
     }
//--- Ausfüllen der Intervallfrequenzen
   for(int i=0; i<size; i++)
     {
      int ind=int((data[i]-minv)/width);
      if(ind>=cells)
         ind=cells-1;
      frequency[ind]++;
     }
   return (true);
  }
  /*
//+------------------------------------------------------------------+
//| Berechnet Werte für die Sequenzerzeugung|
//+------------------------------------------------------------------+
void GetMaxMinStepValues(double &maxv,double &minv,double &stepv)
 {
//--- berechne den absoluten Bereich der Sequenz, um die Normalisierungsgenauigkeit zu erhalten
 double range=MathAbs(maxv-minv);
 int degree=(int)MathRound(MathLog10(range));
//--- normalisiere max. und min. und min. Werte mit der angegebenen Genauigkeit
 maxv=NormalizeDouble(maxv,degree);
 minv=NormalizeDouble(minv,degree);
//---
 stepv=NormalizeDouble(MathPow(10,-degree),degree);
 if((maxv-minv)/stepv<10)
 stepv/=10.;
 }
//+------------------------------------------------------------------+
*/
 
Alexey Klenov:

Ich verstehe, was Ihr Problem war. Ursprünglich sagten Sie, dass der Prozess eine maximale Abweichung von 40 haben kann. Und Sie rechnen mit 40. Aber der Prozess hat die Fähigkeit, sowohl + als auch - zu gehen, so dass Sie am Ende 81 Variationen haben (mit einer genauen 0).

Auf der X-Achse werden 40 Punkte in 2er-Schritten geclustert.

Das ist der Grund, warum Sie ein solches Diagramm haben.

Ich habe die Daten von Excel nach MQL übertragen.

Und mithilfe der Funktionen der Standardbibliothek habe ich Sigma-Parameter ausgewählt, um Ihr Diagramm aus Excel zu wiederholen, wobei ich auch zwangsweise mit Schritt 2 gruppiert habe.

Es stellt sich heraus, dass für Ihren Prozess mit Kombinatorik der Prozess mit einer Normalverteilung von MO 0 und sigma 6,45 geeignet ist.

Oh, das ist interessant. Ja, es gibt einen Bereich von -40...0...40 in 2er Schritten, du hast alles richtig geschrieben. Vielleicht habe ich diesen Punkt im Artikel nicht wiedergekäut. Danke für den Code.
 

Guten Tag

Das blaue Histogramm ist eine Wiederholung Ihres Experiments, nur mit 365 Tagen GBPUSD-Tickdaten

Renko bei 0,0002 Punkten und Unterteilung durch 40 Renko-Balken.

Es wiederholt fast vollständig Ihre theoretische Kurve aus Excel.

Also Ihre Abbildung 7 zu dem Artikel funktioniert nicht.

 

Hier ist der Code

Ich suche nach Fehlern und habe noch keine gefunden.

//+------------------------------------------------------------------+
//|Projektname |
//|Copyright 2020, Firmenname |
//|http://www.firmenname.net |
//+------------------------------------------------------------------+
#include <Graphics\Graphic.mqh>
#include <Math\Stat\Normal.mqh>
#include <Math\Stat\Math.mqh>
#property script_show_inputs
//--- Eingabeparameter
//Eingabe double mean_value=0; // mathematischer Erwartungswert (Mittelwert)
//input double std_dev=1; // Standardabweichung (Standardabweichung)
input double stepRenko=0.0002;   // Der Abstand des Renko-Balkens
//+------------------------------------------------------------------+
//| Skript-Programmstartfunktion|
//+------------------------------------------------------------------+
void OnStart()
  {
//--- Anzeige des Preisdiagramms deaktivieren
   ChartSetInteger(0,CHART_SHOW,false);
//--- Initialisierung des Zufallszahlengenerators
   MathSrand(GetTickCount());
//--- Erzeugen einer Stichprobe der Zufallsvariablen
   long chart=0;
   string name="GraphicNormal";
   int ncells=41;       // Anzahl der Intervalle im Histogramm
   double x[];          // Histogramm-Intervallzentren
   double y[];          // Anzahl der Werte aus der Stichprobe, die in das Intervall fallen
   double data[];       // Stichprobe von Zufallswerten
   double max,min;      // Höchst- und Mindestwerte in der Stichprobe

   MqlTick realTick[];
   ulong start=iTime(_Symbol,PERIOD_D1,365)*1000;         // in ms
   ulong finish=iTime(_Symbol,PERIOD_D1,1)*1000;         // in ms

   int countCopy=CopyTicksRange(_Symbol,realTick,COPY_TICKS_INFO,start,finish);
   Print("countCopy="+IntegerToString(countCopy));
   Print("0 tick time ="+TimeToString(realTick[0].time));
   Print("end tick time ="+TimeToString(realTick[countCopy-1].time));
   
   int index=0;
   double actualStep[];       // Array für Renko-Balken
   ArrayResize(actualStep,countCopy);
   ArrayInitialize(actualStep,0);
   double priceForCheck= realTick[0].bid;
   actualStep[0]=0;
   int cnt=0;

   for(int i=0; i<countCopy; i++)
     {
      if(realTick[i].bid>priceForCheck+stepRenko)
        {
         int add=(int)((realTick[i].bid-priceForCheck)/stepRenko);
         actualStep[index]+=add;
         priceForCheck+=stepRenko*(double)add;
         cnt+=add;
         if(cnt>39)
           {
            index++;
            cnt=0;
           }
         continue;
        }
      if(realTick[i].bid<priceForCheck-stepRenko)
        {
         int add=(int)((priceForCheck-realTick[i].bid)/stepRenko);
         actualStep[index]-=add;
         priceForCheck-=stepRenko*(double)add;
         cnt+=add;
         if(cnt>39)
           {
            index++;
            cnt=0;
           }
        }
     }
   ArrayResize(actualStep,index+1);
   Print("Count index="+IntegerToString(index));
   CalculateHistogramArrayItsMy(actualStep,x,y,max,min,ncells);

// Daten aus Excel
   double arrayTeoryX[41]= {-40,-38,-36,-34,-32,-30,-28,-26,-24,-22,-20,-18,-16,-14,-12,-10,-8,-6,-4,-2,0,
                            2,4,6,8,10,12,14,16,18,20,22,24,26,28,30,32,34,36,38,40
                           };
   double arrayTeoryY[41]= {0.00000009,3.63798 E-06,7.09406 E-05,0.000898581,0.008311872,0.059845479,0.349098627,
                            1.695621904,6.994440355,24.86912126,77.09427591,210.2571161,508.121364,1094.415245,
                            2110.657973,3658.473821,5716.365345,8070.162839,10311.87474,11940.06549,12537.06876,
                            11940.06549,10311.87474,8070.162839,5716.365345,3658.473821,2110.657973,1094.415245,
                            508.121364,210.2571161,77.09427591,24.86912126,6.994440355,1.695621904,0.349098627,
                            0.059845479,0.008311872,0.000898581,7.09406 E-05,3.63798 E-06,9.09495 E-08
                           };
   // Skalierung der theoretischen Kurve auf die reale Kurve 
   double div=100000/index;
   for(int i=0; i<ArraySize(arrayTeoryY); i++)
     {
      arrayTeoryY[i]/=div;
     }

   CGraphic graphic;
   if(ObjectFind(chart,name)<0)
      graphic.Create(chart,name,0,0,0,1080,580);
   else
      graphic.Attach(chart,name);
//graphic.BackgroundMain(StringFormat("Normalverteilung mu=%G sigma=%G stepRenko=%G",mean_value,std_dev,stepRenko));
//graphic.BackgroundMain(StringFormat("Normalverteilung mu=%G sigma=%G",mean_value,std_dev));
   graphic.BackgroundMainSize(16);
//--- alle Kurven zeichnen
   graphic.CurveAdd(x,y,CURVE_HISTOGRAM,"Sample").HistogramWidth(6);
   graphic.CurveAdd(arrayTeoryX,arrayTeoryY,CURVE_LINES,"Excel");


//--- alle Kurven zeichnen
   graphic.CurvePlotAll();
   graphic.Update();
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
bool CalculateHistogramArrayItsMy(const double &data[],double &intervals[],double &frequency[],
                                  double &maxv,double &minv,const int cells=10)
  {
   minv=data[ArrayMinimum(data)];
   maxv=data[ArrayMaximum(data)];
   int range=maxv-minv;
   ArrayResize(intervals,range+1);
   ArrayResize(frequency,range+1);
   for(int i=0; i<range+1; i++)
     {
      intervals[i]=minv+i;
     }
   for(int i=0; i<ArraySize(data); i++)
     {
      int ii=(MathAbs(minv)+data[i]);
      //häufigkeit[ii]+=MathAbs(daten[i]);
      frequency[ii]+=1.0;
     }
   return (true);
  }
//+------------------------------------------------------------------+
 
Alexey Klenov:

Guten Tag

Das blaue Histogramm ist eine Wiederholung Ihres Experiments, nur mit 365 Tagen GBPUSD-Tickdaten

Renko bei 0,0002 Pips und 40 Renko-Balken.

Fast vollständig wiederholt Ihre theoretische Kurve aus Excel.

So Ihre Abbildung 7 auf den Artikel funktioniert nicht aus.

Ich habe Minuten-Kerzen zur Analyse verwendet, wenn man sie in zu kleine Blöcke schneidet, gibt es einen Fehler.
Ich habe keine Renko-Balken, der Algorithmus ist ein bisschen anders. Bei Renko-Bars braucht es 2 Pips, um einen Umkehrblock zu bilden, bei mir ist es immer 1x.
Bitte senden Sie mir eine Tick-Historie, ich werde es nächste Woche versuchen und Ihnen zeigen, was ich bekommen habe. Auf Ticks sollte etwas trendy in Idee sein, aber in der Tat, Ticks sind anders, es hängt von der Quelle. Zum Beispiel gibt es auf einigen Demokonten zu viele Ticks, und das führt zu einem Umkehrprozess.
 
Maxim Romanov:
Ich habe Candlesticks im Minutentakt zur Analyse verwendet. Wenn man sie in zu kleine Blöcke schneidet, kommt es zu einem Fehler.
Ich habe keine Renko-Balken, der Algorithmus ist ein bisschen anders. Bei Renko-Bars braucht es 2 Pips, um einen Umkehrblock zu bilden, bei mir ist es immer 1x.
Bitte senden Sie mir eine Tick-Historie, ich werde es nächste Woche versuchen und Ihnen zeigen, was ich bekommen habe. Auf Ticks sollte etwas trendy in Idee sein, aber in der Tat, Ticks sind anders, es hängt von der Quelle. Zum Beispiel gibt es auf einigen Demokonten zu viele Ticks, und das führt zu einem Umkehrprozess.

Das Terminal lädt die Tick-Historie selbst herunter (MT5, Alpari-MT5-Server).

Variante. im Terminal Ctrl +U dann auf der Registerkarte Ticks können Sie alles machen.

 
Die Normalität Ihrer Bestandsverteilung hängt eindeutig von der Anzahl der Beobachtungen ab: Je mehr Beobachtungen, desto normaler ist sie. Sie sollten gleiche Stichprobengrößen vergleichen.
 
Kristian Kafarov:
Die Normalität Ihrer Bestandsverteilung hängt eindeutig von der Anzahl der Beobachtungen ab: Je mehr Beobachtungen, desto normaler ist sie. Sie sollten ähnliche Stichprobengrößen vergleichen.

Bei den im Artikel angeführten Beispielen mag es tatsächlich so aussehen. In Wirklichkeit gibt es jedoch keinen solchen Effekt. Je mehr Stichproben, desto genauer das Ergebnis, aber die Verteilung ist nicht annähernd normal (obwohl es bestimmte Bedingungen gibt, die in der Studie erfüllt werden müssen). Die Art der Verteilung hängt vielmehr von den einzelnen Handelsinstrumenten ab, die alle leicht unterschiedlich sind.

 
Dies ist ein interessanter Ansatz für die Analyse eines flachen Trends. Aber ich halte ihn in der Praxis für nicht sehr akzeptabel. Vielmehr kann das Material der Einarbeitung in einen anderen Aspekt zugeschrieben werden und nicht mehr.
 
Vielen Dank für diesen Marktüberblick und die Erläuterungen