DataCandles ist eine Struktur. Das Array, in das wir die Candlesticks aus der Historie schreiben, ist array[]. Wir müssen sie also als Zeitreihe anlegen, damit ihre Indizierung mit der Indizierung der Kerzen im Diagramm übereinstimmt. D.h. die Nullzelle von array[] entspricht den Candlesticks, die dem aktuellen Datum am nächsten sind.
D.h. 1. wir kopieren Candlesticks in das Array array[], 2. wir machen daraus eine Zeitreihe, und lesen dann Werte daraus in die Struktur.
Sie können ohne array[] tun - schreiben Sie einfach Daten direkt aus dem Chart in die Struktur, aber ich schlug vor, dies für die Kompatibilität mit Five - es ermöglicht, direkt zu kopieren nur in den Indikator mit high[i], low[i] und andere Daten, aber in das Skript oder Expert Advisor, müssen wir zuerst kopieren Sie die notwendigen Geschichte Intervall in das Array, das ich tat.
Es handelt sich also um einen Fehler, der unter "Fehler, Bugs, Fragen" gemeldet werden sollte.
Hier ist ein Prüfskript, das die Zeit der kopierten Candlesticks in den Null- und letzten Zellen von array[] anzeigt:
//+------------------------------------------------------------------+//| TestCopy.mq4 |//| Copyright 2016, Artem A. Trishkin, Skype artmedia70 |//| https://login.mql5.com/ru/users/artmedia70 |//+------------------------------------------------------------------+#property copyright"Copyright 2016, Artem A. Trishkin, Skype artmedia70"#property link"https://login.mql5.com/ru/users/artmedia70"#property version"1.00"#property strict#property script_show_inputsenum enumYN
{
enYes=1, // Да
enNo=0, // Нет
};
//--- input parametersinputint Search_Period=10; // Количество копируемых свечейint searchPeriod=(Search_Period<1)?1:Search_Period;
inputint Delta=2; // Количество пунктов допускаint delta=(Delta<0)?0:Delta;
input enumYN AsSeries=enYes; // Массив array как таймсерияMqlRates array[]; // Массив структур для копирования Open, High, Low, Close, Timestruct DataCandle // Структура для хранения всех совпадений
{
int number_matched; // Количество совпаденийMqlRates reference_candle; // Данные эталонной свечиMqlRates matched_candles[]; // Массив свечей, совпадающих с эталонной по нужному критерию
};
DataCandle dataCandle[]; // Массив структур данных свечей и их совпадений//+------------------------------------------------------------------+//| Script program start function |//+------------------------------------------------------------------+voidOnStart()
{
//---int copy_bars=(int)fmin(Search_Period,Bars(Symbol(),Period())); // количество копируемых свечейint copied=CopyRates(Symbol(),PERIOD_CURRENT,1,copy_bars,array); // копируем данныеif(copied>0) { // если скопировалиArraySetAsSeries(array,AsSeries); // задаём массив как таймсерию или нетArrayResize(dataCandle,copied); // задаём размер структуры равным числу скопированных данныхZeroMemory(dataCandle); // Обнуляем данные в структуре//--- основной цикл по "эталонным" свечам в массиве array. Их параметры будем искать в доп. циклеfor(int i=0; i<copy_bars-1; i++) { // цикл по скопированным данным от начала до "на один меньше размера массива"
dataCandle[i].reference_candle.high=array[i].high; // ищем этот high
dataCandle[i].reference_candle.low=array[i].low; // запомнили low для сравнения
dataCandle[i].reference_candle.time=array[i].time; // запомнили time для вывода в журнал//--- поиск совпадений с эталонной свечой, индексируемой индексом основного цикла iint size=0; // размер массива совпадающих свечейArrayResize(dataCandle[i].matched_candles,size); // Размер массива совпадений в ноль
dataCandle[i].number_matched=size; // Инициализируем количество совпадений нулём//--- теперь ищем совпадения по high свечей в цикле j с high эталонной свечи с индексом ifor(int j=0; j<copy_bars; j++) { // в цикле от i+1 до copy_barsif(j==i) continue; // пропустим свечу "саму себя"//--- если совпадают high эталонной свечи (i) и свечи с индексом j (с допуском на величину Point)if(NormalizeDouble(delta*Point()-fabs(array[i].high-array[j].high),Digits())>=0) {
size++;
ArrayResize(dataCandle[i].matched_candles,size); // увеличим размер массива совпадающих свечей
dataCandle[i].number_matched=size; // запишем количество совпадений
dataCandle[i].matched_candles[size-1].high=array[j].high; // запишем в массив high совпадающей свечи
dataCandle[i].matched_candles[size-1].low=array[j].low; // запишем в массив low совпадающей свечи
dataCandle[i].matched_candles[size-1].time=array[j].time; // запишем в массив время совпадающей свечи//Print("Время свечи ",i," :",TimeToString(dataCandle[i].reference_candle.time=array[i].time),", high=",DoubleToString(dataCandle[i].reference_candle.high=array[i].high,Digits()),". Совпадение со свечой ",TimeToString(dataCandle[i].matched_candles[size-1].time=array[j].time),", её high ",DoubleToString(dataCandle[i].matched_candles[size-1].high=array[j].high,Digits()),". Совпадений: ",(string)dataCandle[i].number_matched);
}
}
}
}
//--- Посмотрим чего понаписали в массивыAlert("Array is series: ",ArrayIsSeries(array),
"\ntime array[0]: ",TimeToString(array[0].time,TIME_DATE|TIME_MINUTES),
"\ntime array[",string(searchPeriod-1),"]: ",TimeToString(array[ArraySize(array)-1].time,TIME_DATE|TIME_MINUTES));
for(int i=0; i<ArraySize(dataCandle)-1; i++) {
string refs_txt="";
string matched_txt="";
refs_txt="Свеча "+IntegerToString(i,2,'0')+": время "+TimeToString(dataCandle[i].reference_candle.time)+", high: "+DoubleToString(dataCandle[i].reference_candle.high,Digits())+" имеет совпадений: "+(string)dataCandle[i].number_matched+" шт. ";
if(dataCandle[i].number_matched>0) {
for(int j=0; j<ArraySize(dataCandle[i].matched_candles); j++) {
matched_txt="Совпадение "+IntegerToString(j+1)+": "+TimeToString(dataCandle[i].matched_candles[j].time)+", high: "+DoubleToString(dataCandle[i].matched_candles[j].high,Digits());
}
}
Print(refs_txt,matched_txt);
}
}
//+------------------------------------------------------------------+
Ich habe es überprüft - immer falsch, aber die Zeit ist korrekt: wenn zu Beginn des Skripts wählen Array-Array als Zeitreihe "Ja", dann:
Array is series: false
time array[0]: 2016.05.1221:00
time array[9]: 2016.05.1212:00
Wenn Sie "Nein" wählen, dann:
Array is series: false
time array[0]: 2016.05.1212:00
time array[9]: 2016.05.1221:00
die Zeiten der Candlesticks, die in das Array geschrieben werden, sind umgekehrt, was bedeutet, dass ArraySetAsSeriess() korrekt funktioniert, aber ArrayIsSeries() nicht, es gibt immer false aus, was ich bereits in den obigen Bug Thread geschrieben habe.
Oh, diese Programmierung. Je weiter man in den Wald....
Verstehen Sie, dass Sie die Richtung der Anordnung nicht kennen müssen. Der Algorithmus sucht nach Wiederholungen. Daher ist es egal, in welcher Reihenfolge die Takte verarbeitet werden.
Vasiliy Sokolov: Verstehen Sie, dass Sie die Richtung der Anordnung nicht kennen müssen. Der Algorithmus sucht nach Wiederholungen. Es spielt also keine Rolle, in welcher Reihenfolge die Takte verarbeitet werden.
es tut. Schließlich muss ich dann wissen, welche Candlesticks eine Übereinstimmung gebildet haben und bei denjenigen, die dem aktuellen Kurs am nächsten sind, den Kurs niedrig nehmen.
Andrey Koldorkin: Sie benötigen. Denn dann muss ich herausfinden, welche Candlesticks eine Übereinstimmung gebildet haben, und den Preis Low vom nächstgelegenen zum aktuellen Preis nehmen.
Hierfür gibt es eine Kerzenzeit in der Struktur, mit der Sie die nächstgelegene Kerze zu jeder gewünschten Zeit finden können.
Und Sie brauchen die Candlestick-Nummern nicht auszugeben - sie stimmen nicht mit den echten Balken-Nummern überein. Denn wir füllen das Array, und die Indizes im Array gehören nur zur Nummer des Candlesticks im Array, nicht im Diagramm.
Ich habe überprüft, was es ausgibt - immer falsch, aber die Zeit ist korrekt: wenn Sie Array-Array als Zeitreihe "Ja" wählen, wenn Sie das Skript ausführen, dann:
Wenn Sie "Nein" wählen, dann:
Die Zeiten der Candlesticks, die in das Array geschrieben werden, sind umgekehrt, was bedeutet, dass ArraySetAsSeriess() korrekt funktioniert, aber ArrayIsSeries() nicht, es gibt immer false aus, was ich bereits in den obigen Bug Thread geschrieben habe.
und fügte dann die Anzahl der Kerzenständer zur Selbstkontrolle hinzu:
Alert("Array ist Serie: ",ArrayIsSeries(array),
"\nKerze "+IntegerToString(0,2,'0')+" time array[0]: ",TimeToString(array[0].time,TIME_DATE|TIME_MINUTES),
"\nSwitch "+IntegerToString(searchperiod-1,2,'0')+" time array[",string(searchperiod-1),"]:",TimeToString(array[ArraySize(array)-1].time,TIME_DATE|TIME_MINUTES));
Artyom Trishkin: Dazu gibt es eine Kerzenzeit in der Struktur, mit der Sie die nächstgelegene Kerze zu jeder gewünschten Zeit finden können.
Nun, egal. es stellt sich heraus, dass die Richtung mit einer Zeile Code ändert. es wird nicht den Prozess zu komplizieren. Aber während ich gerade versuche, herauszufinden, was los ist, werden zumindest die Kerzenständer in meinem Kopf und in der Maschine in der gleichen Reihenfolge sein ))
und fügte dann die Anzahl der Kerzenständer zur Selbstkontrolle hinzu:
Alert("Array ist Serie: ",ArrayIsSeries(array),
"\nKerze "+IntegerToString(0,2,'0')+" time array[0]: ",TimeToString(array[0].time,TIME_DATE|TIME_MINUTES),
"\nSwitch "+IntegerToString(searchperiod-1,2,'0')+" time array[",string(searchperiod-1),"]:",TimeToString(array[ArraySize(array)-1].time,TIME_DATE|TIME_MINUTES));
Das Ergebnis ist die folgende Ausgabe:
Array ist Serie: false
Kerze 00 Zeit array[0]: 2016.05.12 22:00
Kerze 09 time array[9]: 2016.05.12 13:00
Verwenden Sie mql4? Wenn ja, ermitteln Sie die Nummer der Kerze anhand der Uhrzeit, die in der Struktur angegeben ist. iBarShift() wird Ihnen helfen.
DataCandles ist eine Struktur. Das Array, in das wir die Candlesticks aus der Historie schreiben, ist array[]. Wir müssen sie also als Zeitreihe anlegen, damit ihre Indizierung mit der Indizierung der Kerzen im Diagramm übereinstimmt. D.h. die Nullzelle von array[] entspricht den Candlesticks, die dem aktuellen Datum am nächsten sind.
D.h. 1. wir kopieren Candlesticks in das Array array[], 2. wir machen daraus eine Zeitreihe, und lesen dann Werte daraus in die Struktur.
Sie können ohne array[] tun - schreiben Sie einfach Daten direkt aus dem Chart in die Struktur, aber ich schlug vor, dies für die Kompatibilität mit Five - es ermöglicht, direkt zu kopieren nur in den Indikator mit high[i], low[i] und andere Daten, aber in das Skript oder Expert Advisor, müssen wir zuerst kopieren Sie die notwendigen Geschichte Intervall in das Array, das ich tat.
Alert (Serie);
wie hier?
Beide Warnungen sind immer noch falsch
Alert (Serie);
wie hier?
Beide Warnungen sind immer noch falsch
Es handelt sich also um einen Fehler, der unter "Fehler, Bugs, Fragen" gemeldet werden sollte.
Hier ist ein Prüfskript, das die Zeit der kopierten Candlesticks in den Null- und letzten Zellen von array[] anzeigt:
Dies ist also ein Fehler, der unter "Fehler, Bugs, Fragen" gemeldet werden sollte.
Hier ist ein Prüfskript, das die Zeit der kopierten Candlesticks in den Null- und letzten Zellen von array[] anzeigt:
Dies wird ausgegeben:
Array ist Serie: false
Zeit array[0]: 2016.05.12 21:00
Uhrzeit array[9]: 2016.05.12 12:00
Das Ergebnis ist folgendes:
Array ist Serie: false
Zeit array[0]: 2016.05.12 21:00
Uhrzeit array[9]: 2016.05.12 12:00
Ich habe es überprüft - immer falsch, aber die Zeit ist korrekt: wenn zu Beginn des Skripts wählen Array-Array als Zeitreihe "Ja", dann:
Wenn Sie "Nein" wählen, dann:
die Zeiten der Candlesticks, die in das Array geschrieben werden, sind umgekehrt, was bedeutet, dass ArraySetAsSeriess() korrekt funktioniert, aber ArrayIsSeries() nicht, es gibt immer false aus, was ich bereits in den obigen Bug Thread geschrieben habe.
Oh, diese Programmierung. Je weiter man in den Wald....
Verstehen Sie, dass Sie die Richtung der Anordnung nicht kennen müssen. Der Algorithmus sucht nach Wiederholungen. Es spielt also keine Rolle, in welcher Reihenfolge die Takte verarbeitet werden.
Sie benötigen. Denn dann muss ich herausfinden, welche Candlesticks eine Übereinstimmung gebildet haben, und den Preis Low vom nächstgelegenen zum aktuellen Preis nehmen.
Hierfür gibt es eine Kerzenzeit in der Struktur, mit der Sie die nächstgelegene Kerze zu jeder gewünschten Zeit finden können.
Und Sie brauchen die Candlestick-Nummern nicht auszugeben - sie stimmen nicht mit den echten Balken-Nummern überein. Denn wir füllen das Array, und die Indizes im Array gehören nur zur Nummer des Candlesticks im Array, nicht im Diagramm.
Ich habe überprüft, was es ausgibt - immer falsch, aber die Zeit ist korrekt: wenn Sie Array-Array als Zeitreihe "Ja" wählen, wenn Sie das Skript ausführen, dann:
Wenn Sie "Nein" wählen, dann:
Die Zeiten der Candlesticks, die in das Array geschrieben werden, sind umgekehrt, was bedeutet, dass ArraySetAsSeriess() korrekt funktioniert, aber ArrayIsSeries() nicht, es gibt immer false aus, was ich bereits in den obigen Bug Thread geschrieben habe.
Ich habe den Code leicht geändert:
ArraySetAsSeries(array,true); //hier einfach true eingeben
und fügte dann die Anzahl der Kerzenständer zur Selbstkontrolle hinzu:
Alert("Array ist Serie: ",ArrayIsSeries(array),
"\nKerze "+IntegerToString(0,2,'0')+" time array[0]: ",TimeToString(array[0].time,TIME_DATE|TIME_MINUTES),
"\nSwitch "+IntegerToString(searchperiod-1,2,'0')+" time array[",string(searchperiod-1),"]:",TimeToString(array[ArraySize(array)-1].time,TIME_DATE|TIME_MINUTES));
Das Ergebnis ist die folgende Ausgabe:
Array ist Serie: false
Kerze 00 Zeit array[0]: 2016.05.12 22:00
Kerze 09 time array[9]: 2016.05.12 13:00
Dazu gibt es eine Kerzenzeit in der Struktur, mit der Sie die nächstgelegene Kerze zu jeder gewünschten Zeit finden können.
Ich habe den Code ein wenig geändert:
ArraySetAsSeries(array,true); //hier einfach true eingeben
und fügte dann die Anzahl der Kerzenständer zur Selbstkontrolle hinzu:
Alert("Array ist Serie: ",ArrayIsSeries(array),
"\nKerze "+IntegerToString(0,2,'0')+" time array[0]: ",TimeToString(array[0].time,TIME_DATE|TIME_MINUTES),
"\nSwitch "+IntegerToString(searchperiod-1,2,'0')+" time array[",string(searchperiod-1),"]:",TimeToString(array[ArraySize(array)-1].time,TIME_DATE|TIME_MINUTES));
Das Ergebnis ist die folgende Ausgabe:
Array ist Serie: false
Kerze 00 Zeit array[0]: 2016.05.12 22:00
Kerze 09 time array[9]: 2016.05.12 13:00