ChartID-Eingabeparameter Null in einigen Funktionen führt nicht zur Neuberechnung der Werte. Wenn Sie die aktuellen Daten des aktuellen Diagramms wünschen, müssen Sie die vollständige ID verwenden.
Wenn wir davon ausgehen, dass dies ein normales MT5-Verhalten ist und keine Besonderheit des Broker-Hacks, dann
ORDER_STATE_PARTIAL kommt in historischen Aufträgen nicht vor.
Ausgeführte Aufträge haben immer den Status ORDER_STATE_FILLED.
Wenn ein Auftrag teilweise ausgeführt wird, wird ein entsprechender neuer Marktauftrag vom Handelsserver angelegt (ORDER_REASON_CLIENT - auch wenn der ursprüngliche Auftrag automatisch erteilt wurde (EXPERT)).
Der alte Live-Auftrag (das Ticket wird nicht geändert) bleibt mit einem reduzierten Volumen (ORDER_VOLUME_CURRENT) anhängig.
Der alte Live-Auftrag hat in diesem Fall den Status ORDER_STATE_PARTIAL. Eigentlich ist dieses Kennzeichen das Ergebnis des Vergleichs von ORDER_VOLUME_CURRENT und ORDER_VOLUME_INITIAL.
Alle offenen Positionen erhalten eine ID == OrderTicket. Dabei ist OrderTicket das vom Handelsserver generierte Ticket.
Ein Geschäft hat immer genau einen historischen Auftrag, und sein Status ist ORDER_STATE_FILLED.
Jeder ausgeführte historische Auftrag hat genau einen Abschluss.
Das ORDER_VOLUME_INITIAL eines ausgeführten Auftrags ist gleich dem Volumen, für das er ausgeführt wurde. D.h. selbst der ursprüngliche Auftrag, der storniert wurde, hat ein ORDER_VOLUME_INITITAL, das dem Volumen des von ihm ausgelösten Handels entspricht.
Der Zeitpunkt des ursprünglichen Auftrags (der teilweise ausgeführt wurde) ändert sich nicht und ist nicht gleich dem Zeitpunkt seines Abschlusses.
Die Historientabelle ist nach Auftragszeit (ORDER_TIME_SETUP), nicht aber nach Geschäftszeit sortiert. Wenn wir also HistorySelect from DEAL_TIME ausführen, können wir die entsprechende Bestellung nicht in die History-Tabelle übernehmen.
HistorySelectByPosition liefert immer die erforderliche Menge an Geschäften/Aufträgen.
Sie können die Slippage für jeden Handel berechnen.
Schwachstellen
Es fehlen die Angaben ORDER_REASON_PARTIAL, DEAL_REASON_PARTIAL und POSITION_REASON_PARTIAL. Diese Flags müssen in den jeweiligen Auflistungen unmittelbar nach REASON_EXPERT gesetzt werden.
Entsprechende Marktaufträge können bei der teilweisen Ausführung von Limit-Aufträgen naturgemäß einen negativen Slippage aufweisen. Dies scheint nur ein Fehler in der Auftragsart zu sein, und es gibt wirklich keinen Marktauftrag - er wird nur innerhalb von MT5 erstellt und geht nicht nach außen.
(nicht sicher, schwer zu überprüfen, ähnlich wie bei der teilweisen Schließung von Positionen)
Das Ganze funktioniert folgendermaßen:
1) Pending Order teilweise ausgelöst - Position mit Position_ID = Order_Ticket1 wird eröffnet
2) der verbleibende Auftrag wird in einen neuen Auftrag Order_Ticket2 umgewandelt und wartet auf seine Ausführung; der neue Auftrag_Ticket2 != Order_Ticket1, da es nicht 2 Aufträge mit dem gleichen Order_Ticket in der Historie geben kann
3) der verbleibende Auftrag wurde ausgeführt - eine Position mit Position_ID = Order_Ticket2 wird eröffnet
es gibt zwei Aufträge in der Geschichte, zwei Positionen im Terminal, alles entspricht
Eröffnung einer BUY-Position von Hand auf zwei Trading-Demo-Servern
RoboForex-MetaTrader 5
2018.02.13 00:02:08.424 '8520459': market buy 1.00 GBPUSD
2018.02.13 00:02:10.101 '8520459': accepted market buy 1.00 GBPUSD
2018.02.13 00:02:10.101 '8520459': deal #90389019 buy 1.00 GBPUSD at 1.38387 done (based on order #107426544)
2018.02.13 00:02:10.101 '8520459': order #107426544 buy 1.00 / 1.00 GBPUSD at 1.38387 done in 1683.949 ms
FXOpen-MT5
2018.02.13 00:00:25.780 '18000903': market buy 1.00 GBPUSD
2018.02.13 00:00:25.912 '18000903': accepted market buy 1.00 GBPUSD
2018.02.13 00:00:25.922 '18000903': market buy 1.00 GBPUSD placed for execution
2018.02.13 00:00:25.942 '18000903': order #896454 buy 1.00 / 1.00 GBPUSD at market done in 154.252 ms
2018.02.13 00:00:25.942 '18000903': deal #80559 buy 1.00 GBPUSD at 1.38387 done (based on order #896454)
Die gleichfarbigen Linien bedeuten das Gleiche. Es ist jedoch klar ersichtlich, dass sie in unterschiedlicher Reihenfolge angeordnet sind. Im Robo kommt die Nachricht über die Auftragsausführung, nachdem der Handel ausgeführt wurde. Im Offenen kommt es VOR! Aus diesem Grund liefert OrderSend zwar Glück, aber noch keine Transaktion. D.h. wir erhalten unsynchronisierte OrderSend mit der Historie
Wenn ein Auftrag an ein externes Handelssystem gesendet wird, wartet der MetaTrader 5 Handelsserver nicht auf eine Antwort von diesem und gibt das Ergebnis der Anfrage sofort als "Auftrag erteilt" zurück. Aus diesem Grund wird OrderSend immer deal=0 zurückgeben, da es noch keine Informationen über den ausgeführten Handel gibt. Fangen Sie es in OnTrade oder OnTradeTransaction ab.
OrderSend - sendet einen Auftrag zur Ausführung eines Marktgeschäfts.Der Auftrag wird erteilt- wir müssen Result.order lesen. Aber niemand wartet auf das Geschäft oder die Geschäfte - es kann viele davon geben und die Gesamtdauer ihrer Ausführung ist nicht festgelegt.
Dies hängt von der spezifischen Implementierung der Ausgabe auf der Seite des Brokers ab. Im allgemeinen Fall ist sie nicht definiert.
Ich empfehle Ihnen daher, das Demokonto auf FXOpen-MT5 als Test für Ihren Code zu verwenden, da es sich von anderen Demos abhebt.
Zum Beispiel schlage ich vor, zu versuchen, ein Skript in MQL5 mit solchen Handelslogik (MQL4-Stil nur für schnelle Sinn Anzeige) zu schreiben
Der Posten war groß. Ich habe nicht erwartet, dass ich gelöscht werde. Ich würde gerne den Grund für die Entfernung erfahren. Denn es ist masochistisch, wieder gelöscht zu werden.
Ich sage Ihnen, es ist nicht unter den gelöschten. Vielleicht gab es eine Störung?
Im MT5 funktionieren die Dinge überhaupt nicht gut. Beispiel für das Problem
// Пример неправильного считывания торгового окружения на каждом тике// Скрипт эмулирует два тика ТС, которая должна открыть одну позицию, если ее нет.#include <Trade/Trade.mqh>
// Возвращает количество позиций по символуint GetAmountPositions( conststring Symb )
{
int Res = 0;
// Этот MQL5-код с ошибкойfor (int i = PositionsTotal() - 1; i >= 0; i--)
if (PositionGetSymbol(i) == Symb)
Res++;
/*
// В MT4 такой код выполняется без ошибки
for (int i = OrdersTotal() - 1; i >= 0; i--)
if (OrderSelect(i, SELECT_BY_POS) && (OrderType() <= OP_SELL) && (OrderSymbol() == Symb))
Res++;
*/return(Res);
}
// Пример OnTickvoid ExampleOnTick()
{
static CTrade Trade;
// Если нет позиции, открываемif (!GetAmountPositions(_Symbol))
Trade.Buy(1);
}
// Эмуляция прихода двух Tick-событийvoidOnStart()
{
ExampleOnTick();
Sleep(10); // Между двумя тиками ~10 мс.
ExampleOnTick();
}
Was glauben Sie, was passiert, wenn Sie dieses Skript auf ein Symbol ohne Positionen anwenden?
Die richtige Antwort lautet, dass eine oder zwei Stellen geschaffen werden.
Der Grund dafür ist, dass dies geschieht. Nach dem ersten OrderSend erscheint ein Marktauftrag, und wenn ein neuer Tick vor dem Zeitpunkt seiner Ausführung kommt, gibt es noch keine Position und der zweite OrderSend wird ausgeführt.
Aus diesem Grund wird ein scheinbar normales MT5-Musternicht richtig funktionieren, und infolgedessen werden die meisten MT5-EAs in der kodobase.
Als Beweis für diese Aussage können wir fast jeden Expert Advisor in der MT5 kodobase nehmen. Lassen Sie uns nicht irgendetwas auswählen, sondern nehmen Sie den neuesten Expert Advisor, den es derzeit gibt. Es ist gut, dass es von einem Autor geschrieben wurde, der viel Erfahrung mit MT5-Publishing in QB hat.
Der Quellcode enthält die folgenden Strings (meine Kommentare sind hervorgehoben)
//+------------------------------------------------------------------+//| Expert tick function |//+------------------------------------------------------------------+voidOnTick()
{
//....int total=0; // для расчета количества открытых советником позиций//....//--- main cyclefor(int i=PositionsTotal()-1;i>=0;i--)
if(m_position.SelectByIndex(i)) // selects the position by index for further access to its propertiesif(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==m_magic)
{
total++; // расчет количества открытых позиций//....if(total==0) // Если нет открытых советником позиций
{
if(!RefreshRates())
{
PrevBars=iTime(1);
return;
}
//--- open BUY if(MACD_MAIN_2>MACD_SIGNAL_2 && MACD_MAIN_4<MACD_SIGNAL_4) // Сигнал на покупку
{
double sl=(InpStopLoss!=0)?m_symbol.Ask()-ExtStopLoss:0.0;
double tp=(InpTakeProfit!=0)?m_symbol.Ask()+ExtTakeProfit:0.0;
OpenBuy(sl,tp); // Отправка маркет-ордера на покупкуreturn;
}
//--- open SELLif(MACD_MAIN_2<MACD_SIGNAL_2 && MACD_MAIN_4>MACD_SIGNAL_4) // Сигнал на продажу
{
double sl=(InpStopLoss!=0)?m_symbol.Bid()+ExtStopLoss:0.0;
double tp=(InpTakeProfit!=0)?m_symbol.Bid()-ExtTakeProfit:0.0;
OpenSell(sl,tp); // Отправка маркет-ордера на продажу
}
}
return;
}
Wir haben eine identische Situation wie die oben beschriebene.
Nach dem ersten OrderSend erscheint ein Marktauftrag, und wenn ein neuer Tick vor seiner Ausführung kommt, gibt es noch keine Position und ein zweiter OrderSend wird ausgeführt.
Die scheinbar gute Idee von PositionsTotal wird etwas überschattet von der Notwendigkeit, in MT5 auch OrdersTotal für Marktaufträge zu analysieren.
Das bedeutet, dass der Expert Advisor im allgemeinen Fall statt einer Position zwei, drei usw. öffnet. Je nachdem, wie oft Ticks empfangen werden und wie lange Marktaufträge ausgeführt werden.
Da fast alle MT5 EAs in der kodobase mit der gleichen Logik wie das MT5 Template geschrieben sind, haben sie auch den gleichen Fehler, der darin enthalten ist. Dies gilt leider für fast alle MT5 EAs in KB.
При поступлении сигнала противоположная позиция закрывается. Также советник может закрывать половину позиции (параметр Profit for closing half of the position), может переводить позицию в безубыток (параметр Breakeven). Размер открываемой позиции может задавать вручную (параметр Lots) или в процентах риска от свободной маржи (параметр Risk in...
Bei einem Netting können gleichzeitig eine offene Position und mehrere Marktaufträge in beiden Richtungen für dasselbe Symbol vorliegen. Zum Beispiel eine KAUFEN-Position und ein KAUFEN-Auftrag. Es stimmt, ich habe es nicht geschafft, ein solches Demokonto zu finden, weil es überall eine Regel mit Asynchronität gab
Anhand der Zeitspalte und der numerischen Daten des EA können wir sehr gut erkennen, dass die Dauer der Ausführung eines Handelsauftrags keinen Einfluss auf die Abfolge der OnTradeTransaction-Ereignisse hat. Die ganze Asynchronität geht zum Teufel! Sie haben es geschafft, es so sehr zu vermasseln. Baujahr 1755.
Wenn z. B. OrderSendAsync Market Order im Terminal platziert wird, erscheint die Market Order nicht einmal für einen Moment. Vielleicht haben sich die Entwickler dazu entschlossen, um die Dinge ein wenig zu beschleunigen.
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
Wie erkennt man einen Kartenersatz?
fxsaber, 2018.02.08 12:39
ChartID-Eingabeparameter Null in einigen Funktionen führt nicht zur Neuberechnung der Werte. Wenn Sie die aktuellen Daten des aktuellen Diagramms wünschen, müssen Sie die vollständige ID verwenden.
Forum zum Thema Handel, automatisierte Handelssysteme und Strategietests
POSITIONS_TICKET != POSITIONS_IDENTIFIKATOR
fxsaber, 2018.02.12 20:14
Schlussfolgerungen
Wenn wir davon ausgehen, dass dies ein normales MT5-Verhalten ist und keine Besonderheit des Broker-Hacks, dann
Schwachstellen
ZZY Vollständig bestätigte Hypothese.
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
POSITIONS_TICKET != POSITIONS_IDENTIFIKATOR
Pavel Kolchin, 2018.02.12 13:31
(nicht sicher, schwer zu überprüfen, ähnlich wie bei der teilweisen Schließung von Positionen)
Das Ganze funktioniert folgendermaßen:
1) Pending Order teilweise ausgelöst - Position mit Position_ID = Order_Ticket1 wird eröffnet
2) der verbleibende Auftrag wird in einen neuen Auftrag Order_Ticket2 umgewandelt und wartet auf seine Ausführung; der neue Auftrag_Ticket2 != Order_Ticket1, da es nicht 2 Aufträge mit dem gleichen Order_Ticket in der Historie geben kann
3) der verbleibende Auftrag wurde ausgeführt - eine Position mit Position_ID = Order_Ticket2 wird eröffnet
es gibt zwei Aufträge in der Geschichte, zwei Positionen im Terminal, alles entspricht
Forum zum Thema Handel, automatische Handelssysteme und Testen von Handelsstrategien
Diskussion über "LifeHack für Trader: ForEach auf Defines mischen (#define)"
fxsaber, 2018.02.14 10:54
Leistungsmessung
Ergebnis
Ich lag völlig falsch! SymbolInfoDouble ist doppelt so langsam wie SymbolInfoTick.
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
Diskussion über "LifeHack für Trader: ForEach auf Defines mischen (#define)"
fxsaber, 2018.02.14 11:58
Inkompetent. Ergebnis im Tester.
Wenn Leistung erforderlich ist (Optimierer), ist es besser , SymbolInfoDouble zu verwenden. In der realen Welt macht das keinen Unterschied.
ZZY Function Geschwindigkeitsmessung sollte in einer Umgebung gemessen werden, in der Leistung wichtig ist - Tester.
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
Wanzen, Wanzen, Fragen
fxsaber, 2018.02.12 23:10
Eröffnung einer BUY-Position von Hand auf zwei Trading-Demo-Servern
RoboForex-MetaTrader 5
FXOpen-MT5
Die gleichfarbigen Linien bedeuten das Gleiche. Es ist jedoch klar ersichtlich, dass sie in unterschiedlicher Reihenfolge angeordnet sind. Im Robo kommt die Nachricht über die Auftragsausführung, nachdem der Handel ausgeführt wurde. Im Offenen kommt es VOR! Aus diesem Grund liefert OrderSend zwar Glück, aber noch keine Transaktion. D.h. wir erhalten unsynchronisierte OrderSend mit der Historie
Code für FXOpen-MT5
Ergebnis
Für diese Situation gibt es folgende Erklärung
Forum zum Thema Handel, automatisierte Handelssysteme und Strategietests
Wanzen, Wanzen, Fragen
Rashid Umarov, 2018.02.15 06:25
Wenn ein Auftrag an ein externes Handelssystem gesendet wird, wartet der MetaTrader 5 Handelsserver nicht auf eine Antwort von diesem und gibt das Ergebnis der Anfrage sofort als "Auftrag erteilt" zurück. Aus diesem Grund wird OrderSend immer deal=0 zurückgeben, da es noch keine Informationen über den ausgeführten Handel gibt. Fangen Sie es in OnTrade oder OnTradeTransaction ab.
Ein Beispiel für einen Handels-Ereignis-Listener finden Sie im Artikel Where to start when creating a trading robot for MOEX - TradeTransactionListener.mq5
OrderSend - sendet einen Auftrag zur Ausführung eines Marktgeschäfts.Der Auftrag wird erteilt- wir müssen Result.order lesen. Aber niemand wartet auf das Geschäft oder die Geschäfte - es kann viele davon geben und die Gesamtdauer ihrer Ausführung ist nicht festgelegt.
Dies hängt von der spezifischen Implementierung der Ausgabe auf der Seite des Brokers ab. Im allgemeinen Fall ist sie nicht definiert.
Ich empfehle Ihnen daher, das Demokonto auf FXOpen-MT5 als Test für Ihren Code zu verwenden, da es sich von anderen Demos abhebt.
Zum Beispiel schlage ich vor, zu versuchen, ein Skript in MQL5 mit solchen Handelslogik (MQL4-Stil nur für schnelle Sinn Anzeige) zu schreiben
Das ist gar nicht so einfach. Ich empfehle auch den erwähnten Demoserver, um an der Teilausführung zu arbeiten.
Ich habe einen Beitrag gelöscht, der eine Erklärung für einen der häufigsten Fehler auf MT5 enthielt.
Der Posten war groß. Ich habe nicht erwartet, dass ich gelöscht werde. Ich würde gerne den Grund für die Entfernung erfahren. Denn es ist masochistisch, wieder gelöscht zu werden.
Forum zum Thema Handel, automatische Handelssysteme und Testen von Handelsstrategien
Organisieren einer Auftragsschleife
fxsaber, 2018.02.16 09:40
Im MT5 funktionieren die Dinge überhaupt nicht gut. Beispiel für das Problem
Was glauben Sie, was passiert, wenn Sie dieses Skript auf ein Symbol ohne Positionen anwenden?
Die richtige Antwort lautet, dass eine oder zwei Stellen geschaffen werden.
Der Grund dafür ist, dass dies geschieht. Nach dem ersten OrderSend erscheint ein Marktauftrag, und wenn ein neuer Tick vor dem Zeitpunkt seiner Ausführung kommt, gibt es noch keine Position und der zweite OrderSend wird ausgeführt.
Aus diesem Grundfunktioniert ein scheinbar normales MT5-Musternicht richtig, und als Folge davon funktionieren die meisten MT5 Expert Advisors in Codobase nicht mehr. Gleichzeitig wird das nahezu identische MT4-Template weiterhin problemlos funktionieren.
Die scheinbar gute Idee von PositionsTotal wird etwas überschattet von der Notwendigkeit, in MT5 auch OrdersTotal für Marktaufträge zu analysieren.
Seien Sie vorsichtig!
Aus diesem Grund wird ein scheinbar normales MT5-Musternicht richtig funktionieren, und infolgedessen werden die meisten MT5-EAs in der kodobase.
Als Beweis für diese Aussage können wir fast jeden Expert Advisor in der MT5 kodobase nehmen. Lassen Sie uns nicht irgendetwas auswählen, sondern nehmen Sie den neuesten Expert Advisor, den es derzeit gibt. Es ist gut, dass es von einem Autor geschrieben wurde, der viel Erfahrung mit MT5-Publishing in QB hat.
Der Quellcode enthält die folgenden Strings (meine Kommentare sind hervorgehoben)
Wir haben eine identische Situation wie die oben beschriebene.
Forum für Handel, automatisierte Handelssysteme und Strategietests
Eigenheiten der Sprache mql5, Tipps und Tricks
fxsaber, 2018.02.16 19:52
Nach dem ersten OrderSend erscheint ein Marktauftrag, und wenn ein neuer Tick vor seiner Ausführung kommt, gibt es noch keine Position und ein zweiter OrderSend wird ausgeführt.
Die scheinbar gute Idee von PositionsTotal wird etwas überschattet von der Notwendigkeit, in MT5 auch OrdersTotal für Marktaufträge zu analysieren.
Das bedeutet, dass der Expert Advisor im allgemeinen Fall statt einer Position zwei, drei usw. öffnet. Je nachdem, wie oft Ticks empfangen werden und wie lange Marktaufträge ausgeführt werden.
Da fast alle MT5 EAs in der kodobase mit der gleichen Logik wie das MT5 Template geschrieben sind, haben sie auch den gleichen Fehler, der darin enthalten ist. Dies gilt leider für fast alle MT5 EAs in KB.
Bei einem Netting können gleichzeitig eine offene Position und mehrere Marktaufträge in beiden Richtungen für dasselbe Symbol vorliegen. Zum Beispiel eine KAUFEN-Position und ein KAUFEN-Auftrag. Es stimmt, ich habe es nicht geschafft, ein solches Demokonto zu finden, weil es überall eine Regel mit Asynchronität gab
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
Wanzen, Wanzen, Fragen
fxsaber, 2018.02.14 08:58
Die gesamte OnTradeTransaction-Ereignissequenz erfolgt nach Abschluss des OrderSend.
EA
Manuelles Senden eines Handelsauftrags.
Protokoll
2018.02.14 09:41:46.671 '8854170': instant sell 1.00 EURUSD at 1.23673 2018.02.14 09:41:46.853 '8854170': accepted instant sell 1.00 EURUSD at 1.23673 2018.02.14 09:41:46.853 '8854170': deal #192088422 sell 1.00 EURUSD at 1.23673 done (based on order #208541700) 2018.02.14 09:41:46.853 '8854170': order #208541700 sell 1.00 / 1.00 EURUSD at 1.23673 done in 190.608 msExpert Advisor Ergebnis
Anhand der Zeitspalte und der numerischen Daten des EA können wir sehr gut erkennen, dass die Dauer der Ausführung eines Handelsauftrags keinen Einfluss auf die Abfolge der OnTradeTransaction-Ereignisse hat. Die ganze Asynchronität geht zum Teufel! Sie haben es geschafft, es so sehr zu vermasseln. Baujahr 1755.
Wenn z. B. OrderSendAsync Market Order im Terminal platziert wird, erscheint die Market Order nicht einmal für einen Moment. Vielleicht haben sich die Entwickler dazu entschlossen, um die Dinge ein wenig zu beschleunigen.
Forum zum Thema Handel, automatisierte Handelssysteme und Testen von Handelsstrategien
Diskussion zum Artikel "Visualisierung der Handelsstrategieoptimierung in MetaTrader 5"
fxsaber, 2018.02.22 08:39
Im Rahmenmodus werden OnInit, OnDeinit, OnTick, OnTrade, OnTradeTransaction und OnTimer ignoriert. Nur OnChartEvent funktioniert.
Wegen der OnChartEvent-Ausnahme ist natürlich eine obligatorische Überprüfung des Frame-Mode-Flags erforderlich.