
Handel mit dem MQL5 Wirtschaftskalender (Teil 1): Beherrschung der Funktionen des MQL5-Wirtschaftskalenders
Einführung
In diesem Artikel untersuchen wir die leistungsstarken Funktionen des MetaQuotes Language 5 (MQL5) Wirtschaftskalender und wie sie in den algorithmischen Handel integriert werden können. Der Wirtschaftskalender, der in das Handelsterminal MetaTrader 5 integriert ist, ist ein wichtiges Instrument für Händler, das wichtige Nachrichten und Daten liefert, die die Marktbewegungen erheblich beeinflussen können. Wenn wir verstehen, wie wir diese Informationen abrufen und interpretieren können, haben wir einen Vorteil bei der Vorhersage von Marktreaktionen auf wirtschaftliche Ereignisse und können unsere Handelsstrategien entsprechend anpassen.
Wir beginnen mit einem Überblick über den MQL5-Wirtschaftskalender, seine wichtigsten Komponenten und seine Funktionsweise. Als Nächstes werden wir uns auf die Implementierung in MQL5 konzentrieren und zeigen, wie man programmatisch auf Nachrichtenereignisse im Diagramm zugreifen und diese anzeigen kann. Abschließend fassen wir die gewonnenen Erkenntnisse und die Vorteile der Einbeziehung des Wirtschaftskalenders in Handelssysteme zusammen. Hier sind die Unterthemen, die wir in dem Artikel behandeln werden:
- Überblick über den MQL5-Wirtschaftskalender
- Implementation in MQL5
- Schlussfolgerung
Am Ende dieses Artikels werden Sie mit dem Wissen ausgestattet sein, um einen MQL5 Expert Advisor zu entwickeln, der den MQL5-Wirtschaftskalender effektiv in Ihren Handelsstrategien einsetzt. Fangen wir an.
Überblick über den MQL5-Wirtschaftskalender
Der MQL5-Wirtschaftskalender ist ein hervorragendes Instrument, das den Händlern aktuelle und kohärente Informationen über die wichtigsten Wirtschaftsereignisse liefert, die einen erheblichen Einfluss auf die Finanzmärkte haben können. Es handelt sich um ein nützliches Tool, das sogar noch zugänglicher ist, da es in die MetaTrader 5-Plattform integriert ist.
Der Wirtschaftskalender bietet einen guten Überblick über die verschiedenen anstehenden Ereignisse, die die Finanzmärkte beeinflussen könnten. Von Zinsentscheidungsterminen, Berichten auf Inflation und Gross Domestic Product (Bruttoinlandsprodukt, BIP) bis hin zu Beschäftigungsstatistiken und vielem mehr ist alles dabei. Da jeder dieser Faktoren die Märkte in erheblichem Maße beeinflussen kann - insbesondere bei Währungen, Rohstoffen und Aktien - ist der Kalender ein echtes Muss für kurz- und langfristige Händler.
Um den Kalender zu öffnen, navigieren Sie zur Taskleiste und wählen Sie „Ansicht“ oder „View“ und dann zu „Terminal“ oder „Toolbox“. Nachfolgend finden Sie eine Abbildung.
Sobald das Toolbox bzw. Terminal-Fenster geöffnet ist, navigieren Sie zur Registerkarte „Kalender“ und klicken Sie darauf. Daraufhin öffnet sich das Kalenderfenster, das wie unten abgebildet aussehen sollte.
Es ist erwähnenswert, dass der MQL5-Wirtschaftskalender bevorstehende Ereignisse, die für die Märkte von Bedeutung sind, in geordneter Weise auflistet, sortiert nach ihren erwarteten Auswirkungen. Sie kennzeichnet jeden einzelnen durch eine klare, nicht eindeutige Bezeichnung für den Grad seines potenziellen Einflusses: „gering“, „mittel“ oder „hoch“. So ist es sehr einfach, dem Kalender zu entnehmen, welche kommenden Ereignisse von großer Bedeutung sind und welche nicht. Der Kalender filtert die Ereignisse auch gut nach ihrer Währungsrelevanz. Obwohl die Ereignisse nach Relevanz geordnet und farblich gekennzeichnet sind, gibt es nicht so viele, dass ein Händler bei dem Versuch, sie alle zu berücksichtigen, überwältigt werden könnte. So sorgt der Filtermechanismus dafür, dass die Händler nicht mit irrelevanten Daten überschüttet werden, sondern sich auf die Nachrichten konzentrieren können, die sich direkt auf ihre offenen Positionen oder Handelsstrategien auswirken könnten.
Einer der Hauptvorteile des MQL5-Wirtschaftskalenders ist seine Integration in MQL5, die es Händlern ermöglicht, programmatisch auf Wirtschaftsdaten zuzugreifen und sie in ihre Expert Advisors (EAs) oder automatisierten Handelssysteme einzubinden. Mit den vordefinierten Funktionen können wir Daten wie den Namen des Ereignisses, die geplante Zeit, das Land und den prognostizierten oder tatsächlichen Wert abrufen. Diese Funktionalität ermöglicht es Händlern, Systeme zu entwickeln, die automatisch auf wichtige Nachrichtenereignisse reagieren, sei es durch das Schließen von Positionen zur Vermeidung von Volatilität, das Eröffnen von Geschäften auf der Grundlage von Prognosen oder das Anpassen von Stop-Loss und Take-Profit. Dieser Automatisierungsgrad stellt sicher, dass die Handelsstrategien stets auf die neuesten wirtschaftlichen Entwicklungen reagieren, ohne dass manuelle Eingriffe erforderlich sind. Um die wichtigsten Funktionen des MQL5-Wirtschaftskalenders zusammenzufassen, finden Sie hier eine detaillierte visuelle Darstellung.
Aus dem Bild geht hervor, dass die Daten in 8 Spalten dargestellt sind. Der erste enthält den Zeitpunkt des Ereignisses, der zweite das Währungssymbol, der dritte den Namen des Ereignisses, der vierte den Prioritäts- oder Wichtigkeitsgrad der Nachrichtendaten, der fünfte den Datenzeitraum, während der sechste, siebte und achte die aktuellen, prognostizierten bzw. früheren oder überarbeiteten Daten enthält.
Natürlich sind nicht alle Daten für einen Händler von großer Bedeutung, und so kann man die nicht benötigten Daten auf vier Arten herausfiltern. Zum einen nach Zeit, wenn man zum Beispiel nicht an den bereits veröffentlichten Daten interessiert ist. Die zweite Möglichkeit ist die Filterung nach Währung und die dritte die nach Land. Man könnte mit dem Paar „AUDUSD“ handeln, und somit sind die Nachrichten, die von großer Bedeutung sind, die, die entweder Australien oder die Vereinigten Staaten direkt betreffen. Somit haben die Nachrichten aus China keine signifikanten Auswirkungen auf das Paar.
Schließlich gibt es noch den Wichtigkeits- oder Prioritätsfilter, der dabei hilft, die Nachrichten nach ihrer Bedeutung zu sortieren. Um einen der Filter anzuwenden, klicken Sie einfach mit der rechten Maustaste in das Kalenderfeld und wenden Sie den Filter entsprechend an. Dies wird im Folgenden nochmals veranschaulicht.
Durch die Verwendung des MQL5-Wirtschaftskalenders können Händler ihre Handelspläne im Vorfeld von einflussreichen Marktereignissen besser formulieren. Dies kann entweder durch manuelle Überprüfung des Kalenders im MetaTrader 5 oder durch automatisierte Handelsstrategien geschehen, die auf die Daten des Kalenders reagieren. Dieses Setup ebnet den Weg, um den MQL5-Wirtschaftskalender klar zu verstehen und herauszufinden, wie man ihn in seinem MetaTrader 5-Handelssystem einsetzen kann, um klarere Trades und eine klarere Handelsstrategie zu haben.
Implementation in MQL5
Um einen Expert Advisor (EA) zu erstellen, klicken Sie auf Ihrem MetaTrader 5-Terminal auf die Registerkarte Tools und aktivieren Sie MetaQuotes Language Editor oder drücken Sie einfach F4 auf Ihrer Tastatur. Alternativ können Sie auch auf das IDE-Symbol (Integrated Development Environment) in der Symbolleiste klicken. Dadurch wird die MetaQuotes-Spracheditor-Umgebung geöffnet, die das Schreiben von Handelsrobotern, technischen Indikatoren, Skripten und Funktionsbibliotheken ermöglicht.
Sobald der MetaEditor geöffnet ist, navigieren Sie in der Symbolleiste zur Registerkarte „Datei“ und wählen Sie „Neue Datei“, oder drücken Sie einfach die Tastenkombination STRG + N, um ein neues Dokument zu erstellen. Alternativ könnten wir auch auf das Symbol New auf der Registerkarte Werkzeuge klicken. Daraufhin erscheint ein Popup-Fenster des MQL-Assistenten.
In dem sich öffnenden Assistenten markieren wir die Option Expert Advisor (Template bzw. Vorlage) und klicken auf Weiter (Next).
Wir geben in den allgemeinen Eigenschaften des Expert Advisors unter dem Abschnitt Name den Dateinamen Ihres Experten an. Nicht vergessen, den Backslash vor dem Namen des EA verwenden, um einen Ordner anzugeben oder zu erstellen, wenn er nicht existiert. Hier haben wir zum Beispiel standardmäßig „Experts\“. Das bedeutet, dass unser EA im Ordner Experts erstellt wird und wir ihn dort finden können. Die anderen Abschnitte sind ziemlich einfach, aber Sie können dem Link am Ende des Assistenten folgen, um zu erfahren, wie der Prozess genau abläuft.
Nachdem Sie den gewünschten Expert Advisor-Dateinamen eingegeben haben, klicken Sie auf Weiter, dann auf Weiter und schließlich auf Fertig stellen. Nachdem wir all dies getan haben, können wir nun unsere Strategie programmieren.
Zunächst definieren wir einige Metadaten über den Expert Advisor (EA). Dazu gehören der Name des EA, die Copyright-Informationen und ein Link zur MetaQuotes-Website. Wir geben auch die Version des EA an, die auf „1.00“ eingestellt ist.
//+------------------------------------------------------------------+ //| MQL5 NEWS CALENDAR PART 1.mq5 | //| Copyright 2024, ALLAN MUNENE MUTIIRIA. #@Forex Algo-Trader. | //| https://forexalgo-trader.com | //+------------------------------------------------------------------+ #property copyright "Copyright 2024, ALLAN MUNENE MUTIIRIA. #@Forex Algo-Trader" #property link "https://forexalgo-trader.com" #property description "MQL5 NEWS CALENDAR PART 1" #property version "1.00"
An diesem Punkt müssen wir zunächst die Strukturen für die Arbeit mit dem Wirtschaftskalender verstehen. Es gibt drei davon: MqlCalendarCountry, das die Länderbeschreibungen festlegt, MqlCalendarEvent, das Ereignisbeschreibungen festlegt, und MqlCalendarValue, das die Ereigniswerte festlegt. Ihre Strukturmethoden sind wie folgt.
Kalender Länderstruktur:
struct MqlCalendarCountry { ulong id; // country ID (ISO 3166-1) string name; // country text name (in the current terminal encoding) string code; // country code name (ISO 3166-1 alpha-2) string currency; // country currency code string currency_symbol; // country currency symbol string url_name; // country name used in the mql5.com website URL };
Struktur der Kalenderereignisse:
struct MqlCalendarEvent { ulong id; // event ID ENUM_CALENDAR_EVENT_TYPE type; // event type from the ENUM_CALENDAR_EVENT_TYPE enumeration ENUM_CALENDAR_EVENT_SECTOR sector; // sector an event is related to ENUM_CALENDAR_EVENT_FREQUENCY frequency; // event frequency ENUM_CALENDAR_EVENT_TIMEMODE time_mode; // event time mode ulong country_id; // country ID ENUM_CALENDAR_EVENT_UNIT unit; // economic indicator value's unit of measure ENUM_CALENDAR_EVENT_IMPORTANCE importance; // event importance ENUM_CALENDAR_EVENT_MULTIPLIER multiplier; // economic indicator value multiplier uint digits; // number of decimal places string source_url; // URL of a source where an event is published string event_code; // event code string name; // event text name in the terminal language (in the current terminal encoding) };
Struktur der Kalenderwerte:
struct MqlCalendarValue { ulong id; // value ID ulong event_id; // event ID datetime time; // event date and time datetime period; // event reporting period int revision; // revision of the published indicator relative to the reporting period long actual_value; // actual value multiplied by 10^6 or LONG_MIN if the value is not set long prev_value; // previous value multiplied by 10^6 or LONG_MIN if the value is not set long revised_prev_value; // revised previous value multiplied by 10^6 or LONG_MIN if the value is not set long forecast_value; // forecast value multiplied by 10^6 or LONG_MIN if the value is not set ENUM_CALENDAR_EVENT_IMPACT impact_type; // potential impact on the currency rate //--- functions checking the values bool HasActualValue(void) const; // returns true if actual_value is set bool HasPreviousValue(void) const; // returns true if prev_value is set bool HasRevisedValue(void) const; // returns true if revised_prev_value is set bool HasForecastValue(void) const; // returns true if forecast_value is set //--- functions receiving the values double GetActualValue(void) const; // returns actual_value or nan if the value is no set double GetPreviousValue(void) const; // returns prev_value or nan if the value is no set double GetRevisedValue(void) const; // returns revised_prev_value or nan if the value is no set double GetForecastValue(void) const; // returns forecast_value or nan if the value is no set };
Als Erstes müssen wir nun alle Werte sammeln, die innerhalb eines Zeitraums unserer Auswahl verfügbar sind, und sie speziell nach den Werten sortieren, von denen wir acht gesehen haben, sowie die Filter anwenden. Um die Werte zu erhalten, wenden wir die folgende Logik an.
MqlCalendarValue values[]; datetime startTime = TimeTradeServer() - PeriodSeconds(PERIOD_D1); datetime endTime = TimeTradeServer() + PeriodSeconds(PERIOD_D1); int valuesTotal = CalendarValueHistory(values, startTime, endTime, NULL, NULL); Print("TOTAL VALUES = ", valuesTotal, " || Array size = ", ArraySize(values));
Hier deklarieren wir das Array „values“ vom Typ MqlCalendarValue-Struktur, das die vom MQL5-Wirtschaftskalender abgerufenen Wirtschaftskalenderdaten enthalten wird. Anschließend richten wir zwei Variablen vom Typ datetime ein, „startTime“ und „endTime“, die den Zeitbereich für die Datenextraktion festlegen. Wir berechnen die Startzeit der Werte als einen Tag vor der aktuellen Serverzeit, die mit der Funktion TimeTradeServer abgerufen wird, und verwenden die Funktion PeriodSeconds, um einen 24-Stunden-Versatz in Sekunden zu erstellen. Die eintägige Zeitlogik wird durch die Verwendung der Konstante „PERIOD_D1“ erreicht. In ähnlicher Weise wird „endTime“ auf einen Tag nach der aktuellen Serverzeit gesetzt, sodass wir wirtschaftliche Ereignisse erfassen können, die innerhalb von zwei Tagen um den gegenwärtigen Zeitpunkt herum auftreten.
Als Nächstes verwenden wir die Funktion CalendarValueHistory, um das Werte-Array mit wirtschaftlichen Ereignissen innerhalb des angegebenen Zeitraums aufzufüllen. Diese Funktion gibt die Gesamtzahl der Ereignisse zurück, die wir in der Variablen „valuesTotal“ speichern. Die Parameter für CalendarValueHistory umfassen das Array „values“, „startTime“ und „endTime“ sowie zwei NULL-Filter für Land und Währungstyp (wir lassen sie hier NULL, um alle Ereignisse abzurufen). Schließlich verwenden wir die Funktion Print, um die Gesamtzahl der Werte und die Größe des Arrays mit der Funktion ArraySize auszudrucken, um die Gesamtzahl der erhaltenen Ereignisse zu bestätigen und zu überprüfen, ob das Array die erwarteten Daten für die weitere Verwendung in unserer Handelslogik enthält. Wenn wir dies kompilieren, erhalten wir die folgende Ausgabe.
Als Nächstes können wir diese Werte im Protokoll ausdrucken, um zu überprüfen, was wir haben.
if (valuesTotal >=0 ){ Print("Calendar values as they are: "); ArrayPrint(values); }
Hier wird zunächst geprüft, ob die Gesamtwerte größer oder gleich Null sind, was bedeutet, dass die Funktion CalendarValueHistory erfolgreich einige wirtschaftliche Kalenderereignisse abgerufen hat oder fehlerfrei Null zurückgegeben hat. Wenn diese Bedingung erfüllt ist, verwenden wir die Funktion Drucken, um die Meldung „Calendar values as they are:“ (Kalenderwerte wie sie sind) als Kopfzeile auszugeben, um uns darüber zu informieren, dass die Werte nun angezeigt werden. Anschließend rufen wir die Funktion ArrayPrint auf, die den gesamten Inhalt des Arrays „values“ in das Protokoll ausgibt. Nach der Ausführung erhalten wir die folgenden Daten.
Aus dem Bild ist ersichtlich, dass wir alle verfügbaren Ereignisse innerhalb des ausgewählten Zeitrahmens protokollieren. Wir können jedoch sehen, dass die Ereignismerkmale nur durch Ziffern dargestellt werden, die als Merkmalsbezeichner spezifisch sind und uns nicht viele Informationen liefern. Wir müssen also einen bestimmten Wert auswählen, und von dort aus können wir die spezifischen Merkmale für jedes Ereignis strukturiert abrufen. Das bedeutet, dass wir jeden ausgewählten Wert in einer Schleife durchlaufen müssen.
for (int i = 0; i < valuesTotal; i++){ //--- }
Hier erstellen wir eine for-Schleife, die über jedes Element im Array „values" iteriert, das die Wirtschaftskalenderdaten enthält. Die Schleife initialisiert eine ganzzahlige Variable „i" auf Null, die den Startindex darstellt, und läuft so lange, wie „i" kleiner ist als die Gesamtwerte, d. h. die Gesamtzahl der von der Funktion CalendarValueHistory abgerufenen Ereignisse. Bei jeder Iteration wird „i“ um eins erhöht, sodass wir auf jedes wirtschaftliche Ereignis im Array „Werte“ nacheinander zugreifen können. Innerhalb der Schleife können wir nun die Daten jedes einzelnen Ereignisses verarbeiten oder analysieren, was Flexibilität für Aufgaben wie das Filtern von Ereignissen, die Anwendung spezifischer Handelslogik auf der Grundlage von Ereignisdetails oder das Drucken einzelner Ereignisinformationen bietet. Hier ist die Logik, die wir anwenden müssen.
MqlCalendarEvent event; CalendarEventById(values[i].event_id,event);
Wir deklarieren eine Variable „event“ vom Typ MqlCalendarEvent, die die detaillierten Informationen für ein bestimmtes wirtschaftliches Ereignis speichern wird. Dann rufen wir CalendarEventById auf und übergeben zwei Parameter. Der erste Parameter ruft die eindeutige ID des aktuellen Wirtschaftsereignisses aus dem Array „values“ ab (basierend auf dem aktuellen Schleifenindex i), während der zweite, „event“, als Container zum Speichern der vollständigen Details des Ereignisses dient. Mit der Funktion CalendarEventById haben wir Zugriff auf umfassende Daten zu jedem einzelnen Ereignis, wie z. B. Name, Land, Vorhersage und tatsächliche Werte, die wir dann für zusätzliche Analysen oder Handelsentscheidungen nutzen können. Um dies zu bestätigen, können wir die Ereignis-ID wie folgt drucken.
Print("Event ID ",values[i].event_id);
Dies würde jedoch zu viele Daten im Protokoll ausgeben, weshalb wir den Zeitbereich auf eine Stunde vor und nach der aktuellen Zeit reduzieren. Wir müssen nur den Abschnitt mit den Punkten ändern. Wir haben sie zur besseren Orientierung gelb markiert.
datetime startTime = TimeTradeServer() - PeriodSeconds(PERIOD_H1); datetime endTime = TimeTradeServer() + PeriodSeconds(PERIOD_H1);
Wenn wir das Programm ausführen, erhalten wir die folgende Ausgabe.
Wir können nun fortfahren, um die tatsächlichen Werte des ausgewählten Ereignisses zu erhalten, mit Ausnahme der Ziffern der Ereigniswerte. Um dies zu erreichen, müssen wir nur das Schlüsselwort „event“ eingeben und den „Punktoperator“ verwenden, um Zugriff auf alle Methoden und Objekte dieser Klasse oder Struktur zu erhalten. Hier ist, was Sie bekommen sollten.
Mit der gleichen Methode können wir alle Informationen abrufen, die wir in die von uns erstellte Struktur „event“ eingegeben und gespeichert haben.
Print("Event ID ",values[i].event_id); Print("Event Name = ",event.name); Print("Event Code = ",event.event_code); Print("Event Type = ",event.type); Print("Event Sector = ",event.sector); Print("Event Frequency = ",event.frequency); Print("Event Release Mode = ",event.time_mode); Print("Event Importance = ",EnumToString(event.importance)); Print("Event Time = ",values[i].time); Print("Event URL = ",event.source_url); Comment("Event ID ",values[i].event_id, "\nEvent Name = ",event.name, "\nEvent Code = ",event.event_code, "\nEvent Type = ",event.type, "\nEvent Sector = ",event.sector, "\nEvent Frequency = ",event.frequency, "\nEvent Release Mode = ",event.time_mode, "\nEvent Importance = ",EnumToString(event.importance), "\nEvent Time = ",values[i].time, "\nEvent URL = ",event.source_url); }
Hier verwenden wir die Druckfunktionen, um Details zu jedem wirtschaftlichen Ereignis im Werte-Array auszugeben und diese Informationen auf der Registerkarte Experten zur einfachen Überprüfung anzuzeigen. Zunächst wird die Ereignis-ID aus values[i] ausgedruckt, die das Ereignis eindeutig identifiziert. Als Nächstes werden spezifische Details über das Ereignis aus der Variablen „event“ abgerufen und ausgedruckt, einschließlich Name, Ereigniscode, Typ, Sektor, Häufigkeit, Zeitmodus (der den Zeitmodus für die Freigabe angibt), Wichtigkeit (mit der Funktion EnumToString in eine lesbare Zeichenkette umgewandelt) und der tatsächlichen geplanten Zeit. Schließlich drucken wir den Uniform Resource Locator (URL) der Quelle aus, der einen Link zu weiteren Informationen enthält.
Neben diesen Druckanweisungen verwenden wir die Funktion Kommentar, um dieselben Details auf dem Diagramm zur sofortigen Bezugnahme anzuzeigen. Die Funktion Comment gibt jede Zeile im Kommentarbereich des Charts aus, was es dem Händler erleichtert, Echtzeit-Updates direkt im Chart zu sehen. Nachdem das Programm ausgeführt wurde, erhalten wir die folgende Ausgabe.
Das war ein Erfolg. Um Zugang zu den Länder- und Währungsdaten zu erhalten, integrieren wir eine weitere Struktur, die die Länderwerte verarbeitet. Hier ist die Logik, die wir übernehmen müssen und die mit den anderen, die wir verwendet haben, identisch ist.
MqlCalendarCountry country; CalendarCountryById(event.country_id,country);
Hier wird eine Variable „country“ vom Typ MqlCalendarCountry deklariert, in der die länderspezifischen Informationen über das wirtschaftliche Ereignis gespeichert werden sollen. Anschließend verwenden wir die Funktion CalendarCountryById, um die Länderdetails abzurufen, indem wir zwei Parameter übergeben.
Der erste Parameter gibt die eindeutige Kennung des Landes an, das mit dem aktuellen Wirtschaftsereignis verbunden ist, während der Parameter „country“ als Container für die Daten dieses Landes dient. Durch den Aufruf der Funktion CalendarCountryById füllen wir unsere Variable „country“ mit relevanten Informationen, wie dem Namen, dem Code und anderen Merkmalen des Landes, sodass wir diese Daten für eine kontextbezogene Analyse verwenden und länderspezifische Details zusammen mit jedem wirtschaftlichen Ereignis anzeigen können.
Um dies anzuzeigen, drucken wir erneut die Länderinformationen aus.
Print("Country ID ",country.id); Print("Country Name ",country.name); Print("Country Code ",country.code); Print("Country Currency ",country.currency); Print("Country Currency Symbol ",country.currency_symbol); Print("Country URL ",country.url_name);
Dies ist das Ergebnis, wenn wir das Programm ausführen.
Das war ein Erfolg. Wir haben nun eine vollständige Einführung in die notwendigen Funktionen in MQL5, die uns den Zugriff auf die Kalenderdaten ermöglichen. Nun können wir unseren Codeblock mit Filtern versehen, die in der Regel länderspezifische Daten, Prioritätsdaten, Währungen und zeitabhängige Nachrichten enthalten. Um dies dynamisch zu erreichen, können wir unsere Logik in eine Funktion verlagern, die wir für den oben genannten Zweck verwenden können.
//+------------------------------------------------------------------+ //| FUNCTION TO GET NEWS EVENTS | //+------------------------------------------------------------------+ bool isNewsEvent(){ int totalNews = 0; bool isNews = false; //--- return (isNews); }
Wir definieren eine boolesche Funktion namens „isNewsEvent“, die feststellt, ob Wirtschaftsnachrichten verfügbar sind. Die Funktion gibt einen boolschen Wert zurück, der angibt, ob ein Nachrichtenereignis vorliegt (true) oder nicht (false). Innerhalb der Funktion deklarieren wir eine Integer-Variable „totalNews“ und initialisieren sie mit Null. In dieser Variablen soll die Gesamtzahl der relevanten Nachrichtenereignisse gespeichert werden, die wir später in der Funktion abrufen werden. Wir deklarieren auch eine boolsche Variable, „isNews“, und setzen sie auf false. Diese Variable dient als Flagge, die auf true gesetzt wird, wenn während der Ausführung der Funktion relevante Nachrichtenereignisse entdeckt werden.
Derzeit gibt die Funktion lediglich den Wert von „isNews“ zurück, der standardmäßig falsch ist, da noch keine Nachrichtenereignisse in der Funktion verarbeitet werden. Diese Funktionsstruktur bildet die Grundlage für die Implementierung einer Logik, mit der später Nachrichtenereignisse abgerufen und geprüft werden können, wobei „isNews“ auf „true“ gesetzt wird, wenn Ereignisse erkannt werden. Zu dieser Funktion fügen wir unsere zuvor bereits definierte Logik aus der Ereignisbehandlung von OnInit hinzu. Wir rufen jedoch die Funktion des Event-Handlers auf, um die Logik unserer Funktion zu beeinflussen.
//+------------------------------------------------------------------+ //| Expert initialization function | //+------------------------------------------------------------------+ int OnInit(){ //--- if (isNewsEvent()){ Print("______ ALERT: WE HAVE NEWS EVENT ___"); } else if (isNewsEvent()==false){ Print("______ ALERT: WE DON'T ANY HAVE NEWS EVENT ___"); } //--- return(INIT_SUCCEEDED); }
Hier, innerhalb von OnInit, beginnen wir mit dem Aufruf der Funktion „isNewsEvent“. Wenn die Funktion den Wert true zurückgibt, bedeutet das, dass ein Nachrichtenereignis verfügbar ist, wird der if-Block ausgelöst und die Meldung „______ ALERT: WE HAVE NEWS EVENT ___“ ausgegeben. Diese Meldung weist uns darauf hin, dass ein wirtschaftliches Ereignis erkannt wurde, das wir nutzen können, um unsere Handelsstrategien anzupassen, falls gewünscht.
Wenn sie false zurückgibt, bedeutet das, dass keine neuen Ereignisse vorhanden sind, wird der else if-Block ausgelöst und wir drucken „______ ALERT“: WE DON'T HAVE ANY NEWS EVENT ___“. Diese Meldung weist uns darauf hin, dass keine aktuellen Nachrichtenereignisse identifiziert wurden, was darauf hinweisen kann, dass der Handel ohne zu erwartende Unterbrechungen durch die Nachrichten fortgesetzt werden kann. Schließlich gibt die Funktion INIT_SUCCEEDED zurück, eine Konstante, die anzeigt, dass die Initialisierung des EA erfolgreich war. Nach dem Aufruf von OnInit() können wir nun weiterhin Filter auf die Art von Nachrichten anwenden, die für uns von Bedeutung sind. Derzeit ist das Programm mit dem Symbol „AUDUSD“ verbunden. Wir sollten eine Logik entwickeln, die sicherstellt, dass nur Nachrichten aus den Vereinigten Staaten berücksichtigt werden.
string currency_filter = "USD"; string currency_base = SymbolInfoString(_Symbol,SYMBOL_CURRENCY_BASE); string currency_quote = StringSubstr(_Symbol,3,3); if (currency_base != currency_filter && currency_quote != currency_filter){ Print("Currency (",currency_base," | ",currency_quote, ") is not equal equal to ",currency_filter); return false; }
Wir beginnen mit der Definition von zwei String-Variablen, „currency_filter“ und „currency_base“, um zu prüfen, ob das aktuelle Symbol für den angegebenen Währungsfilter „USD“ relevant ist. Die Variable „currency_filter“ wird mit dem Wert „USD“ initialisiert, der die Zielwährung darstellt, die wir überwachen wollen. Anschließend wird die Basiswährung des aktuellen Symbols (z. B. AUD im AUDUSD-Paar) mit der Funktion SymbolInfoString abgerufen und in „currency_base“ gespeichert.
Als Nächstes definieren wir „currency_quote“ und extrahieren die Kurswährung aus dem aktuellen Symbol, indem wir die letzten drei Zeichen mit der Funktion StringSubstr verwenden, da es keine direkte Möglichkeit gibt, auf die Kurswährung zuzugreifen. Für das Paar AUDUSD beispielsweise ruft die Funktion StringSubstr die Kurswährung „USD“ ab.
Anschließend wird geprüft, ob sich sowohl die Basis- als auch die Kurswährung von der Filterwährung unterscheiden. Wenn sie nicht mit dem Zielwährungsfilter (in diesem Fall USD) übereinstimmen, wird eine Meldung ausgegeben, dass die Währungen des Symbols nicht mit dem Währungsfilter übereinstimmen. Die Funktion gibt dann false zurück und beendet die weitere Verarbeitung, wenn das Symbol für die angegebene Währung irrelevant ist. Wenn wir dies in verschiedenen Symbolen ausführen, erhalten wir die folgende Ausgabe.
Anhand der Visualisierung können wir sehen, dass wir keinen Fehler erhalten, wenn wir das Programm in die Charts „AUDUSD“ und „USDJPY“ laden, aber wenn wir es in den Chart „EURJPY“ laden, erhalten wir einen Fehler, der anzeigt, dass keine der Währungsziffern unserer vordefinierten Filterwährung entspricht. Wir können nun mehrere Filter dynamisch nach der Bedeutung des Ereignisses und dem Zeitpunkt anwenden.
if (StringFind(_Symbol,country.currency) >= 0){ if (event.importance == CALENDAR_IMPORTANCE_MODERATE){ if (values[i].time <= TimeTradeServer() && values[i].time >= timeBefore){ Print(event.name," > ", country.currency," > ", EnumToString(event.importance)," Time= ",values[i].time," (ALREADY RELEASED)"); totalNews++; } if (values[i].time >= TimeTradeServer() && values[i].time <= timeAfter){ Print(event.name," > ", country.currency," > ", EnumToString(event.importance)," Time= ",values[i].time," (NOT YET RELEASED)"); totalNews++; } } }
Wir implementieren eine Reihe von verschachtelten Bedingungen, um relevante Nachrichtenereignisse für eine bestimmte Währung zu identifizieren, wobei wir uns auf Ereignisse konzentrieren, die als „mäßig wichtig“ eingestuft werden und in eine bestimmte Zeitspanne fallen. Zunächst wird geprüft, ob der Name des aktuellen Handelssymbols (dargestellt durch _Symbol) die mit dem Ereignis verbundene Währung enthält. Dazu verwenden wir die Funktion StringFind, die sicherstellt, dass nur Ereignisse berücksichtigt werden, die an die Währung des Handelssymbols gebunden sind.
Dies ist ähnlich wie die andere Logik, die wir verwendet haben, nur dass sie dynamisch ist, indem sie automatisch die Verfügbarkeit der Währung im ausgewählten Symbol überprüft. Ist diese Prüfung erfolgreich, wird die nächste Bedingung erfüllt, um zu bestätigen, dass die Wichtigkeit des Ereignisses mit CALENDAR_IMPORTANCE_MODERATE übereinstimmt, was bedeutet, dass wir nur Ereignisse mit mäßiger Auswirkung berücksichtigen und solche mit geringer oder hoher Wichtigkeit ausschließen.
Sobald wir ein Ereignis von mittlerer Bedeutung identifiziert haben, bewerten wir sein Timing in Bezug auf die aktuelle Zeit des Servers (TimeTradeServer) mit zwei separaten Prüfungen. Bei der ersten Prüfung wird festgestellt, ob der Zeitpunkt des Ereignisses vor oder gleich der aktuellen Zeit, aber nach „timeBefore“ liegt. Wenn ja, bedeutet dies, dass das Ereignis bereits innerhalb des von uns angegebenen Zeitraums veröffentlicht wurde. Mit der Funktion Print werden die Details des Ereignisses protokolliert, darunter der Name, die zugehörige Währung, die Wichtigkeit und die Uhrzeit, wobei das Ereignis als „ALREADY RELEASED“ gekennzeichnet wird. Wir erhöhen auch die Variable „totalNews“, um die Ereignisse zu verfolgen, die unseren Kriterien entsprechen. Bei der zweiten Prüfung wird festgestellt, ob der Zeitpunkt des Ereignisses später oder gleich dem aktuellen Zeitpunkt, aber früher oder gleich „timeAfter“ ist, was bedeutet, dass das Ereignis bevorsteht, aber noch innerhalb des von uns festgelegten Zeitrahmens liegt.
Auch hier protokollieren wir ähnliche Ereignisdetails mit der Druckfunktion, kennzeichnen sie als „NOT YET RELEASED“, um ihren ausstehenden Status anzuzeigen, und erhöhen die Variable „totalNews“ für dieses zusätzliche relevante Ereignis. Sie haben vielleicht bemerkt, dass wir in der Logik verschiedene Zeitvariablen verwendet haben. Diese sollen lediglich sicherstellen, dass das Ereignis innerhalb des Zeitraums liegt, in dem es ausgelöst werden kann.
datetime timeRange = PeriodSeconds(PERIOD_D1); datetime timeBefore = TimeTradeServer() - timeRange; datetime timeAfter = TimeTradeServer() + timeRange; Print("FURTHEST TIME LOOK BACK = ",timeBefore," >>> CURRENT = ",TimeTradeServer());
Wir deklarieren diese Logiken kurz vor der for-Schleife, um einen Zeitbereich um die aktuelle Serverzeit herum festzulegen, um zu definieren, wie weit zurück und vorwärts wir Nachrichtenereignisse berücksichtigen wollen. Zunächst deklarieren wir eine Datetime-Variable, „timeRange“, und weisen ihr mit der Funktion PeriodSeconds die Dauer eines Tages zu. Dies ermöglicht es uns, mit einem standardisierten Zeitrahmen von 24 Stunden zu arbeiten. Sie können diesen jedoch einfach an die von Ihnen gewünschte Spanne anpassen, beispielsweise 15 Minuten vor und nach der Pressemitteilung. Als Nächstes definieren wir zwei zusätzliche Datetime-Variablen: „timeBefore“ und „timeAfter“.
Wir berechnen die Variable „timeBefore“, indem wir die Zeitspanne von der aktuellen Serverzeit subtrahieren, wodurch wir den am weitesten zurückliegenden Zeitpunkt erhalten. In ähnlicher Weise wird „timeAfter“ bestimmt, indem „timeRange“ zur aktuellen Serverzeit addiert wird, was den spätesten Zeitpunkt ergibt, den wir in der Zukunft berücksichtigen wollen. Zusammen bilden „timeBefore“ und „timeAfter“ ein 24-Stunden-Fenster, das um die aktuelle Uhrzeit zentriert ist und uns hilft, Ereignisse zu erfassen, die entweder gerade eingetreten sind oder in Kürze erwartet werden. Hier ist eine Illustration.
Aus dem Bild ist ersichtlich, dass die aktuelle Zeit, oder besser gesagt das Datum, da wir eine eintägige Abfrage in Betracht ziehen, 25 ist, der Rückblick auf das Datum 24 und der Ausblick auf das Datum 26, das nur einen Tag vor und nach dem aktuellen Datum liegt. Wir haben sie zur Verdeutlichung blau hervorgehoben. Schließlich können wir die Anzahl der in der Schleife aufgezeichneten Nachrichten analysieren und die entsprechenden booleschen Flags zurückgeben. Um dies zu erreichen, gehen wir nach folgender Logik vor.
if (totalNews > 0){ isNews = true; Print(">>>>>>> (FOUND NEWS) TOTAL NEWS = ",totalNews,"/",ArraySize(values)); } else if (totalNews <= 0){ isNews = false; Print(">>>>>>> (NOT FOUND NEWS) TOTAL NEWS = ",totalNews,"/",ArraySize(values)); }
Hier bewerten wir, ob relevante Nachrichtenereignisse auf der Grundlage der insgesamt erfassten Nachrichten identifiziert wurden. Wenn die Gesamtzahl der Nachrichten größer als Null ist, bedeutet dies, dass mindestens ein Nachrichtenereignis gefunden wurde, das unseren Kriterien entspricht. In diesem Fall setzen wir die Variable „isNews“ auf true und geben eine Meldung aus, die die Gesamtzahl der übereinstimmenden Nachrichtenereignisse und die Größe des Arrays „values“ anzeigt. Die Nachricht mit der Bezeichnung „FOUND NEWS“ enthält auch die insgesamt ermittelten Nachrichten und alle zunächst berücksichtigten Nachrichten, wobei angegeben wird, wie viele relevante Nachrichtenereignisse von den insgesamt abgerufenen Ereignissen gefunden wurden.
Ist die Gesamtzahl der Nachrichten dagegen gleich Null oder kleiner, bedeutet dies, dass keine relevanten Nachrichten gefunden wurden. In diesem Szenario setzen wir „isNews“ auf false und geben eine Meldung mit der Aufschrift „NOT FOUND NEWS“ aus, die anzeigt, dass die Gesamtzahl der Nachrichten gleich Null ist, sowie die Größe des Arrays „values“. Anhand dieser Struktur können wir verfolgen, ob Nachrichten gefunden wurden, die unseren Kriterien entsprechen, und ein Ergebnisprotokoll erstellen, das zur Überprüfung des Ergebnisses der Nachrichtenüberprüfung nützlich ist. Nach dem Kompilieren erhalten wir die folgende Ausgabe.
Aus dem Bild können wir ersehen, dass es derzeit keine relevanten Nachrichten gibt. Wir können also unsere Suche ausweiten, indem wir den Zeitbereich bzw. den Suchbereich der Ereignisse in diesem Fall auf einen Tag erweitern.
datetime startTime = TimeTradeServer() - PeriodSeconds(PERIOD_D1); datetime endTime = TimeTradeServer() + PeriodSeconds(PERIOD_D1);
Wenn wir den Nachrichtenbereich auf einen Tag zurücksetzen, erhalten wir die folgende Ausgabe.
Aus dem Bild können wir ersehen, dass wir 5 relevante Nachrichten von 81 haben und wir drucken, dass es relevante Nachrichtenereignisse gibt, die wir nutzen können, um Handelsentscheidungen zu treffen, d.h. entweder in den Markt einzusteigen oder aus dem Markt auszusteigen. Das ist alles für diesen Teil und die vollständige Funktion, die für die Identifizierung und das Filtern von Nachrichten aus dem MQL5-Kalender verantwortlich ist, ist wie im folgenden Code-Abschnitt:
//+------------------------------------------------------------------+ //| FUNCTION TO GET NEWS EVENTS | //+------------------------------------------------------------------+ bool isNewsEvent(){ int totalNews = 0; bool isNews = false; MqlCalendarValue values[]; datetime startTime = TimeTradeServer() - PeriodSeconds(PERIOD_D1); datetime endTime = TimeTradeServer() + PeriodSeconds(PERIOD_D1); //string currency_filter = "USD"; //string currency_base = SymbolInfoString(_Symbol,SYMBOL_CURRENCY_BASE); //string currency_quote = StringSubstr(_Symbol,3,3); //if (currency_base != currency_filter && currency_quote != currency_filter){ // Print("Currency (",currency_base," | ",currency_quote, // ") is not equal equal to ",currency_filter); // return false; //} int valuesTotal = CalendarValueHistory(values,startTime,endTime,NULL,NULL); Print("TOTAL VALUES = ",valuesTotal," || Array size = ",ArraySize(values)); //if (valuesTotal >=0 ){ // Print("Calendar values as they are: "); // ArrayPrint(values); //} datetime timeRange = PeriodSeconds(PERIOD_D1); datetime timeBefore = TimeTradeServer() - timeRange; datetime timeAfter = TimeTradeServer() + timeRange; Print("Current time = ",TimeTradeServer()); Print("FURTHEST TIME LOOK BACK = ",timeBefore," >>> LOOK FORE = ",timeAfter); for (int i = 0; i < valuesTotal; i++){ MqlCalendarEvent event; CalendarEventById(values[i].event_id,event); MqlCalendarCountry country; CalendarCountryById(event.country_id,country); if (StringFind(_Symbol,country.currency) >= 0){ if (event.importance == CALENDAR_IMPORTANCE_MODERATE){ if (values[i].time <= TimeTradeServer() && values[i].time >= timeBefore){ Print(event.name," > ", country.currency," > ", EnumToString(event.importance)," Time= ",values[i].time," (ALREADY RELEASED)"); totalNews++; } if (values[i].time >= TimeTradeServer() && values[i].time <= timeAfter){ Print(event.name," > ", country.currency," > ", EnumToString(event.importance)," Time= ",values[i].time," (NOT YET RELEASED)"); totalNews++; } } } } if (totalNews > 0){ isNews = true; Print(">>>>>>> (FOUND NEWS) TOTAL NEWS = ",totalNews,"/",ArraySize(values)); } else if (totalNews <= 0){ isNews = false; Print(">>>>>>> (NOT FOUND NEWS) TOTAL NEWS = ",totalNews,"/",ArraySize(values)); } return (isNews); }
Schlussfolgerung
Zusammenfassend lässt sich sagen, dass wir die ersten Schritte unternommen haben, um den MQL5 Wirtschaftskalender zu erkunden. Es geht darum, Informationen zu extrahieren und sie dann nach der Bedeutung der Währungen und der Bedeutung der Ereignisse zu beurteilen. Wir haben einen strukturierten Prozess entwickelt, der es uns ermöglicht, Daten aus dem Wirtschaftskalender zu ziehen, sie nach wichtigen Kriterien wie Währung und Bedeutung des Ereignisses zu filtern und festzustellen, ob Ereignisse unmittelbar bevorstehen oder bereits eingetreten sind. Dieser Ansatz ist von entscheidender Bedeutung für die Automatisierung von Handelssystemen, die auf wichtige wirtschaftliche Entwicklungen reagieren können und uns einen Vorteil bei der Steuerung von Marktschwankungen verschaffen.
Im nächsten Teil dieser Serie werden wir unsere Funktionalität erweitern, um die gefilterten Wirtschaftsdaten direkt im Chart-Fenster anzuzeigen und so die Sichtbarkeit der Daten für Handelsentscheidungen in Echtzeit zu erhöhen. Wir werden auch unseren Expert Advisor verbessern, damit er diese Informationen nutzen kann, um Handelspositionen auf der Grundlage wichtiger wirtschaftlicher Ereignisse zu eröffnen. Mit diesen integrierten Funktionen werden wir von der Analyse von Wirtschaftsnachrichten zur tatsächlichen Nutzung dieser Nachrichten für den Handel übergehen. Wir werden unsere Systeme reaktionsschneller machen, indem wir einen Echtzeit-Rahmen entwickeln und die aus den Ereignissen des Wirtschaftskalenders gewonnenen Informationen nutzen, um im Anschluss an diese Ereignisse Trades auszulösen. Bleiben Sie am Ball.
Übersetzt aus dem Englischen von MetaQuotes Ltd.
Originalartikel: https://www.mql5.com/en/articles/16223





- 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.