Wie verschiebe ich die Struktur der globalen Variablen im Indikator, wenn ich zu einem anderen Zeitrahmen wechsle? - Seite 4

 
Nikolai Semko:
Ich persönlich nutze die Ressourcen über die Gewerkschaft.
Sogar Arrays von Strukturen können leicht zwischen TFs übertragen werden, ohne dass sie in eine Datei geschrieben werden müssen.

Könnten Sie das näher erläutern? Ich danke Ihnen.

 
Mikhail Nazarenko:

Können Sie das näher erläutern? Ich danke Ihnen.

Ich werde es irgendwann einmal im Buy More aufschreiben.
Hier ist die Klasse dafür.
Und Sie müssen nur zwei Zeilen in den Indikator einfügen:

  • Erstellen Sie eine Instanz dieser Klasse vor dem OnInit und verknüpfen Sie Ihr Array von Strukturen, die zwischen den TFs übergeben werden sollen. Wenn es sich nicht um die erste Initialisierung handelt, wird das Array der Strukturen mit Daten aus der vorherigen TF gefüllt.
  • Bei OnDeinit speichern Sie Ihr Array über eine einzige Methode in dieser Klasse.

template <typename T>
class CStructArr {
 private:
   union StructUint {
      T st;
      uint u[1+sizeof(T)/4];
   };
   string            Name;
   uint              Var[];
   int               w;
   int               h;
   StructUint        su;
   int               size;

 public:
   CStructArr(const string name,T &var[]);
   ~CStructArr();
   bool              Set(T &var[]);
   //bool              Save();
   T                 value[];
};
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
template <typename T>
CStructArr::CStructArr(const string name,T &var[]) {
   //ulong tt=GetMicrosecondCount();
   size = ArraySize(var);
   w=1+size*sizeof(T)/4;
   ArrayResize(Var,w);
   h=1;
   Name="::"+name+ IntegerToString(ChartGetInteger(0,CHART_WINDOW_HANDLE));
   if(ResourceReadImage(Name,Var,w,h)) {
      size = 4*(w-1)/sizeof(T);
      ArrayResize(value,size);
      ArrayResize(var,size);
      for (int j=0; j<size; j++) {
         for(int i=0; i<sizeof(T)/4; i++) su.u[i]=Var[j*sizeof(T)/4+i];
         value[j]=su.st;
         var[j]=value[j];
      }
   } else {
      for (int j=0; j<size; j++) {
         su.st=var[j];
         for(int i=0; i<sizeof(T)/4; i++) Var[j*sizeof(T)/4+i]=su.u[i];
         value[j]=var[j];
      }
      if(!ResourceCreate(Name,Var,w,1,0,0,0,COLOR_FORMAT_XRGB_NOALPHA)) printf("Error create Resource: "+DoubleToString(GetLastError(),0));
   }
   //tt=GetMicrosecondCount()-tt;
   //Print("!!!!!!!!  =  "+string(tt));
}
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
template <typename T>
CStructArr::~CStructArr() {
   if(_UninitReason!=REASON_RECOMPILE && _UninitReason!=REASON_CHARTCHANGE) ResourceFree(Name);
}
//+------------------------------------------------------------------+
template <typename T>
bool CStructArr::Set(T &var[]) {
   size = ArraySize(var);
   ArrayResize(value,size);
   w=1+size*sizeof(T)/4;
   ArrayResize(Var,w);
   for (int j=0; j<size; j++) {
      su.st=var[j];
      for(int i=0; i<sizeof(T)/4; i++) Var[j*sizeof(T)/4+i]=su.u[i];
      value[j]=var[j];
   }
   if(!ResourceCreate(Name,Var,w,1,0,0,0,COLOR_FORMAT_XRGB_NOALPHA)) {
      printf("Error create Resource: "+DoubleToString(GetLastError(),0));
      return(false);
   } else return(true);
}
//+------------------------------------------------------------------+
Die Verwendung globaler Terminalvariablen zur Übergabe von Parametern zwischen TFs ist meiner Meinung nach eine sehr ungeschickte Lösung.
 
Nikolai Semko:

Ich werde es irgendwann in der QB aufschreiben.
Hier ist die Klasse dafür.
Und im Indikator müssen Sie nur zwei Zeilen hinzufügen:

  • Erstellen Sie eine Instanz dieser Klasse vor OnInit und verknüpfen Sie Ihr Array von Strukturen, die zwischen TFs übergeben werden sollen. Wenn es sich nicht um die erste Initialisierung handelt, wird das Array der Strukturen mit Daten aus der vorherigen TF gefüllt.
  • In OnDeinit speichern Sie Ihr Array über eine einzige Methode in dieser Klasse.

Ich halte die Verwendung globaler Terminalvariablen zur Übergabe von Parametern zwischen TFs für eine sehr krumme Lösung.

Danke, das ist alles richtig.

 
Nikolai Semko:

Hier ist die Klasse dafür.

Auf den ersten Blick ist die Implementierung der Umwandlung T[]<->uint[] nicht optimal.
 
fxsaber:
Auf den ersten Blick ist die Implementierung der Umwandlung T[]<->uint[] nicht optimal.

Ich habe diesen Code vor langer Zeit geschrieben. Das mag sein.
Dort gibt es allerdings nicht viel zu optimieren. Vielleicht nur in einigen kleinen Dingen.
Wie auch immer, diese Klasse kann in meinem neuesten kostenlosen Produkt auf dem Markt ausprobiert werden.

Ich wäre Ihnen dankbar, wenn Sie eine bessere Umsetzung vorschlagen könnten.

 
Nikolai Semko:

Ich wäre Ihnen dankbar, wenn Sie eine bessere Umsetzung vorschlagen könnten.

Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien

Bibliotheken: TradeTransactions

fxsaber, 2019.03.15 07:36

// Быстрый кастинг массивов.
#include <fxsaber\TradeTransactions\Convert.mqh> // https://www.mql5.com/ru/code/22166

void OnStart()
{
  MqlTick Ticks[];

  MqlRates Rates[];  
  CopyRates(_Symbol, PERIOD_CURRENT, 0, 10, Rates); // Получили котировки.
  CONVERT::ArrayToArray(Rates, Ticks);              // Кастинг MqlRates[] -> MqlTick[].

  MqlRates Rates2[];    
  CONVERT::ArrayToArray(Ticks, Rates2);             // Кастинг MqlTick[] -> MqlRates[].
  ArrayPrint(Rates2);                               // Убедились, что все корректно.
}
Dateien:
Convert.mqh  4 kb
 
Mikhail Nazarenko:
Wie überträgt man eine globale Variable, Struktur oder ein Objekt in einem Indikator, wenn man zu einem anderen Zeitrahmen wechselt? Ich habe es gegoogelt und konnte es nicht finden.

Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien

Bibliotheken: TradeTransactions

fxsaber, 2018.12.17 23:48

Sie können alles über Ressourcen handeln.

// Пример обмена любыми данными (включая строковые массивы).

#include <fxsaber\TradeTransactions\ResourceData.mqh> // https://www.mql5.com/ru/code/22166

#define  PRINT(A) Print(#A + " = " + (string)(A));

void OnStart()
{    
  // Произвольные данные для примера
  string Str[] = {"123", "Hello World!"};
  double Num = 5;
  MqlTick Tick = {0};
  Tick.bid = 1.23456;

  const RESOURCEDATA<uint> Resource; // Ресурс для обмена данными
  CONTAINER<uint> Container;         // Создаем контейнер - все будет храниться в массиве простого типа (в примере выбран uint)
  
  // Заполняем контейнер разными данными
  Container[0] = Str;
  Container[1] = Num;
  Container[2] = Tick;
    
  // Распечатаем типы хранимых в контейнере данных
  for (int i = 0; i < Container.GetAmount(); i++)
    PRINT(Container[i].GetType())

  Resource = Container.Data;  // Отправили данные на обмен
  
  CONTAINER<uint> Container2; // Сюда будем получать данные
  
  Resource.Get(Container2.Data); // Получили данные
      
  // Получим данные в исходном виде
  string Str2[];
  Container[0].Get(Str2);                // Получили массив
  ArrayPrint(Str2);

  PRINT(Container[1].Get<double>())      // Получили число
  PRINT(Container[2].Get<MqlTick>().bid) // Получили структуру  
}
 
fxsaber:

Leider ist sie nicht unverschämt. Ich werde nicht auf eure Bibeln eingehen.
Ich habe bereits versucht, in Ihren Code hineinzuschauen und festgestellt, dass ich nicht reif genug bin. :))

Wie auch immer, wenn Sie alle Inluder öffnen, wird Ihr Code länger im Quellcode und ausführbar sein.

Auch ein paar Mal verbrannt, wenn ich Ihre Libs verwendet, und dann fand die Quelle der Bremsen für eine lange Zeit, bis sie abgerissen wurden. Danach habe ich aufgegeben.

Die Hauptschwierigkeit bei der Verwendung Ihres Codes, der aus vielen Inludes besteht, ist die hohe Komplexität der Fehlersuche, wenn bei jedem Schritt neue Klassen, Defines oder Makros hinzukommen.
Und ich habe Zeit für den Test, weil ich verstehe, dass es kaum möglich ist, meinen Algorithmus erheblich zu beschleunigen.
Der einzige Fehler, den ich jetzt sehe, ist die Verwendung von Schleifen anstelle von CopyArray an einigen Stellen. Nach dieser Korrektur wird mein Code in Bezug auf Leistung und Lesbarkeit nahezu perfekt sein.

 
Nikolai Semko:

Der einzige Fehler, den ich jetzt sehe, ist, dass ich an einigen Stellen Schleifen anstelle von CopyArray verwende. Nach dieser Korrektur wird mein Code in Bezug auf Leistung und Lesbarkeit nahezu perfekt sein.

Wenn Sie eine Leistungsmessung schreiben, wäre es interessant, diese zu vergleichen.

 

:)

Es ist seltsam, dass niemand über "Krücken", "Neuerfindung des Rades", "Schwierigkeiten bei der Datenübertragung auf ein anderes Terminal","das Problem muss mit MMS-Mitteln gelöst werden " schreibt...
Es stellt sich heraus, dass Lösungen auf der Grundlage von Meta-Zitaten Krücken und mauvais ton sind)