Diskussion zum Artikel "Bibliothek für ein leichtes und schnelles Entwickeln vom Programmen für den MetaTrader (Teil XXI): Handelsklassen - Plattformübergreifendes Basis-Handelsobjekt" - Seite 3

 
Artyom Trishkin:
Wenn Sie eine Handelsanfrage mit einer Position vergleichen müssen, ist es am einfachsten, die Positionskennung zu setzen (keine Magie). Jede Anfrage hat ihre eigene Kennung. Die Magie des Beraters kann für alle Positionen gleich gelassen werden. Anhand der Kennung (sie wird in die Magie einer Position oder eines Auftrags geschrieben und geht nie verloren) können Sie dann die Anfrage und die Position/den Auftrag jederzeit genau abgleichen.

Ist es etwas wie dieses?

Handelsanfrage:

ulong order_magic = m_engine.SetCompositeMagicNumber(m_magic, 0, 0, m_order_id);
bool submit_ok    = m_engine.PlaceBuyLimit(m_lot_size, m_symbol, m_entry, m_hard_stop, m_ratio_target, order_magic, m_comment, m_expiry);

Event Handler:

void CMyRobot::EngineEventHandler(int event_id, const long &lparam, const double &dparam, const string &sparam, bool testing, long chart_id)
{
   if (sparam != m_symbol) return;                                                  //--- Überspringen der Ereignisbehandlung bei nicht übereinstimmenden Symbolen

   if (event_id > SERIES_EVENTS_NO_EVENT && event_id < SERIES_EVENTS_NEXT_CODE) {   //--- BEHANDLUNG VON ZEITREIHENEREIGNISSEN
      if (event_id == SERIES_EVENTS_NEW_BAR) {                                      // Ereignis "neuer Takt": lparam = Zeitraum | dparam = Datum/Uhrzeit
         this.RefreshAllIndicators(1);
         this.ExecuteFSM(1, chart_id);                                              // Ausführen des endlichen Zustandsautomaten (NB: Index des neuen Balkens = 1)
      }
   }
   else
   if (event_id > TRADE_EVENT_NO_EVENT && event_id < TRADE_EVENTS_NEXT_CODE) {      //--- BEHANDLUNG VON HANDELSEREIGNISSEN
      CArrayObj *event_list = m_engine.GetListAllOrdersEvents();                    // Abrufen der Liste der Handelsereignisse
      if (event_list == NULL) return;
      
      //--- Berechnung der Verschiebung des Ereignisindexes relativ zum Ende der Liste
      //--- beim Backtesting wird der Verschiebungswert im Parameter "lparam" an den Event-Handler übergeben
      //--- im normalen Betrieb werden die Handelsereignisse einzeln gesendet und in OnChartEvent() behandelt
      int shift = testing ? (int)lparam : 0;
      CEvent *event = event_list.At(event_list.Total() - 1 - shift);
      if (event == NULL || event.GetPendReqID() != m_order_id) return;
      
      switch (event.TypeEvent())
      {
         case TRADE_EVENT_PENDING_ORDER_PLASED:                                     //--- ausstehender Auftrag erteilt
            if (m_state_curr == FSM_PENDING_ORDER && m_ticket == WRONG_VALUE)
                m_ticket = event.TicketOrderEvent();
            break;
      
         // ...
      }
   }
}
 

Problem: Die Methode CEvent::GetPendReqID(), die ich oben benötige, lautet protected!! Gibt es bessere Ideen, ohne dass ich den DoEasy-Quellcode ändern muss? Meiner bescheidenen Meinung nach, sollten diese Methoden öffentlich sein ;-)

class CEvent : public CObject
  {
//...
protected:
//--- Rückgabe von (1) der angegebenen magischen Zahl, der ID von (2) der ersten Gruppe, (3) der zweiten Gruppe, (4) der ausstehenden Anfrage aus dem Wert der magischen Zahl
   ushort            GetMagicID(void)                          const { return ushort(this.Magic() & 0xFFFF);                                 }
   uchar             GetGroupID1(void)                         const { return uchar(this.Magic()>>16) & 0x0F;                                }
   uchar             GetGroupID2(void)                         const { return uchar((this.Magic()>>16) & 0xF0)>>4;                           }
   uchar             GetPendReqID(void)                        const { return uchar(this.Magic()>>24) & 0xFF;                                }
//...
};
 
Dima Diall :

Problem: Die Methode CEvent::GetPendReqID(), die ich oben benötige, lautet protected !! Gibt es bessere Ideen, ohne dass ich den DoEasy-Quellcode ändern muss? Meiner bescheidenen Meinung nach, sollten diese Methoden öffentlich sein ;-)

Sie müssen die Klasse CEngine im Auge behalten - nur sie gibt Benutzerprogrammen Zugriff auf die Bibliothek.

Alle anderen Klassen sind für die Bedürfnisse der Bibliothek und nicht für die Benutzer gedacht, mit Ausnahme der Bibliotheksdienstfunktionen, die im Programm verfügbar sind, nachdem die Bibliothek mit ihm verbunden wurde.

 
Artyom Trishkin:

Sie müssen die CEngine-Klasse beobachten - nur sie gibt Benutzerprogrammen Zugriff auf die Bibliothek.

Alle anderen Klassen sind für die Bedürfnisse der Bibliothek und nicht für die Benutzer bestimmt, mit Ausnahme der Bibliotheksdienstfunktionen, die im Programm verfügbar sind, nachdem die Bibliothek mit ihm verbunden wurde.

Können Sie mir bitte ein Beispiel geben? Ich schaue mir die Klasse CEngine an und sehe, dass es möglich ist, eine Liste von Ereignissen zu extrahieren, ihren Typ zu überprüfen usw... Ich kann also auf jedes Ereignis zugreifen, finde aber keine offensichtliche Möglichkeit, spezifische Ereignisdetails, die in der magischen Zahl verpackt sind (Gruppen- und Anforderungs-ID), aus dem CEngine-Objekt zu lesen. So wie ich es sehe, muss ich diese Informationen immer noch direkt aus den CEvent-Objektinstanzen lesen, wie in meinem Event-Handler-Beispiel oben in der Even-Handler-Methode meines Roboters, d. h. CEvent:GetPendReq()

class CEngine
  {
//...
//...
//--- Rückgabe (1) der Liste der Order-, Deal- und Positionsereignisse, (2) des Basis-Handelsereignisobjekts nach Index und der (3) Anzahl der neuen Handelsereignisse
   CArrayObj           *GetListAllOrdersEvents(void)                    { return this.m_events.GetList();                     }
   CEventBaseObj       *GetTradeEventByIndex(const int index)           { return this.m_events.GetTradeEventByIndex(index);   }
   int                  GetTradeEventsTotal(void)                 const { return this.m_events.GetTradeEventsTotal();         }
//--- Zurücksetzen des letzten Handelsereignisses
   void                 ResetLastTradeEvent(void)                       { this.m_events.ResetLastTradeEvent();                }
//--- Rückgabe des (1) letzten Handelsereignisses, (2) des letzten Ereignisses in den Kontoeigenschaften und (3) des letzten Ereignisses in den Symboleigenschaften
   ENUM_TRADE_EVENT     LastTradeEvent(void)                      const { return this.m_last_trade_event;                     }
   int                  LastAccountEvent(void)                    const { return this.m_last_account_event;                   }
   int                  LastSymbolsEvent(void)                    const { return this.m_last_symbol_event;                    }
//--- Rückgabe des (1) Hedge-Kontos, (2) Arbeit im Tester, (3) Kontoereignis, (4) Symbol-Ereignis und (5) Handelsereignis-Flag
   bool                 IsHedge(void)                             const { return this.m_is_hedge;                             }
   bool                 IsTester(void)                            const { return this.m_is_tester;                            }
   bool                 IsAccountsEvent(void)                     const { return this.m_accounts.IsEvent();                   }
   bool                 IsSymbolsEvent(void)                      const { return this.m_symbols.IsEvent();                    }
   bool                 IsTradeEvent(void)                        const { return this.m_events.IsEvent();                     }
//...
//...
  };
 
Dima Diall :

Не могли бы вы привести мне пример? Я смотрю на класс CEngine и вижу, что можно извлечь список событий, проверить их тип и т. Д., Поэтому я могу получить доступ к каждому событию, но не нахожу очевидного способа прочитать конкретные детали события, упакованные в магическое число (группы и идентификатор запроса) из объекта CEngine - как я вижу, мне все еще нужно читать эту информацию непосредственно из экземпляров объекта CEvent, как в моем примере обработчика событий выше в методе обработчика четных событий моего робота, то есть CEvent :: GetPendReqID ()

Warten Sie bitte ein wenig. Der nächste Artikel im ru-Segment wird sich mit Beratern beschäftigen, und da werde ich versuchen, das zu erklären.

 
Artyom Trishkin:

Warten Sie bitte ein wenig. Der nächste Artikel im ru-Segment wird sich mit Beratern befassen, und dort werde ich versuchen, das zu erklären.

OK, cool - danke...