Использование индикатора в советнике

 

Подскажите кто может (бьюсь несколько дней) почему при вызове данных индикатора с помощью функции iCustom я получаю данные не такие, какие выводит индикатор при присоединении к графику во время работы с тестером стратегий. Вот код индикатора:

//+------------------------------------------------------------------+
//| DT-ZigZag-Lauer.mq4 |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2005, klot"
#property link "klot@mail.ru"

#property indicator_chart_window
#property indicator_buffers 2
#property indicator_color1 Red
#property indicator_color2 Blue
//---- input parameters
extern int depth=5;
extern int GrossPeriod=240;
//---- buffers
double ExtMapBuffer1[];
double ExtMapBuffer2[];
datetime daytimes[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
//---- indicators
SetIndexStyle(0,DRAW_ARROW);
SetIndexArrow(0,159);
SetIndexBuffer(0,ExtMapBuffer1);
SetIndexEmptyValue(0,0.0);
SetIndexStyle(1,DRAW_ARROW);
SetIndexArrow(1,159);
SetIndexBuffer(1,ExtMapBuffer2);
SetIndexEmptyValue(1,0.0);
double zigzag1;

//----
//----
if (Period()>GrossPeriod) { Alert("DT-ZigZag: Текущий таймфрейм должен быть меньше чем ", GrossPeriod); return(0); }
// Все Time[] серии времени отсортировано в направлении убывания
ArrayCopySeries(daytimes,MODE_TIME,Symbol(),GrossPeriod);
return(0);
}
//+------------------------------------------------------------------+
//| Custor indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----

//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
int counted_bars=IndicatorCounted();
int limit=300,bigshift;
double zigzag1;

if (counted_bars<0) return(-1);

if (counted_bars>0) counted_bars--;

limit=Bars-counted_bars;
//----
for (int i=0; i<limit; i++)
{
if(Time[i]>=daytimes[0]) bigshift=0;
else
{
bigshift = ArrayBsearch(daytimes,Time[i-1],WHOLE_ARRAY,0,MODE_DESCEND);
if(Period()<=GrossPeriod) bigshift++;
}
for (int cnt=bigshift; cnt<(100+bigshift); cnt++)
{
zigzag1=iCustom(NULL,GrossPeriod,"ZigZag",depth,5,3,0,cnt+1);
if ( zigzag1!=0 ) break;
}

if ( iClose(NULL,0,i+1)<=zigzag1 ) ExtMapBuffer2[i]=zigzag1; else ExtMapBuffer2[i]=0.0;

if ( iClose(NULL,0,i+1)>=zigzag1 ) ExtMapBuffer1[i]=zigzag1; else ExtMapBuffer1[i]=0.0;

ObjectsRedraw();
}
Comment("zigzag1 = ",zigzag1);
//----
return(0);
}
//+------------------------------------------------------------------+

В советнике использую вот этот код для визуализации:

if(Month()<10) mm = "0"+Month(); else mm = Month();
if(Day()<10) dd = "0"+Day(); else dd = Day();
if(Hour()<10) hh = "0"+Hour(); else hh = Hour();
if(Minute()<10) mi = "0"+Minute(); else mi = Minute();

и вызываю данные из индикатора, вот так:

double FOR1 = iCustom(NULL,0,"DT-ZigZag-lauer",5,240,0,0);

в результате получаю значения переменной FOR1 при тестировании одни, а при присоединении индикатора в режиме теста его значения другие и даже если совпадают то такое впечатление что это другой таймфрейм, но и то я подобрать его при тестировании не смог.

 
ingenermig:

Подскажите кто может (бьюсь несколько дней) почему при вызове данных индикатора с помощью функции iCustom я получаю данные не такие, какие выводит индикатор при присоединении к графику во время работы с тестером стратегий. Вот код индикатора:

//+------------------------------------------------------------------+
//| DT-ZigZag-Lauer.mq4 |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2005, klot"
#property link "klot@mail.ru"

#property indicator_chart_window
#property indicator_buffers 2
#property indicator_color1 Red
#property indicator_color2 Blue
//---- input parameters
extern int depth=5;
extern int GrossPeriod=240;
//---- buffers
double ExtMapBuffer1[];
double ExtMapBuffer2[];
datetime daytimes[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
//---- indicators
SetIndexStyle(0,DRAW_ARROW);
SetIndexArrow(0,159);
SetIndexBuffer(0,ExtMapBuffer1);
SetIndexEmptyValue(0,0.0);
SetIndexStyle(1,DRAW_ARROW);
SetIndexArrow(1,159);
SetIndexBuffer(1,ExtMapBuffer2);
SetIndexEmptyValue(1,0.0);
double zigzag1;

//----
//----
if (Period()>GrossPeriod) { Alert("DT-ZigZag: Текущий таймфрейм должен быть меньше чем ", GrossPeriod); return(0); }
// Все Time[] серии времени отсортировано в направлении убывания
ArrayCopySeries(daytimes,MODE_TIME,Symbol(),GrossPeriod);
return(0);
}
//+------------------------------------------------------------------+
//| Custor indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----

//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
int counted_bars=IndicatorCounted();
int limit=300,bigshift;
double zigzag1;

if (counted_bars<0) return(-1);

if (counted_bars>0) counted_bars--;

limit=Bars-counted_bars;
//----
for (int i=0; i<limit; i++)
{
if(Time[i]>=daytimes[0]) bigshift=0;
else
{
bigshift = ArrayBsearch(daytimes,Time[i-1],WHOLE_ARRAY,0,MODE_DESCEND);
if(Period()<=GrossPeriod) bigshift++;
}
for (int cnt=bigshift; cnt<(100+bigshift); cnt++)
{
zigzag1=iCustom(NULL,GrossPeriod,"ZigZag",depth,5,3,0,cnt+1);
if ( zigzag1!=0 ) break;
}

if ( iClose(NULL,0,i+1)<=zigzag1 ) ExtMapBuffer2[i]=zigzag1; else ExtMapBuffer2[i]=0.0;

if ( iClose(NULL,0,i+1)>=zigzag1 ) ExtMapBuffer1[i]=zigzag1; else ExtMapBuffer1[i]=0.0;

ObjectsRedraw();
}
Comment("zigzag1 = ",zigzag1);
//----
return(0);
}
//+------------------------------------------------------------------+

В советнике использую вот этот код для визуализации:

if(Month()<10) mm = "0"+Month(); else mm = Month();
if(Day()<10) dd = "0"+Day(); else dd = Day();
if(Hour()<10) hh = "0"+Hour(); else hh = Hour();
if(Minute()<10) mi = "0"+Minute(); else mi = Minute();

и вызываю данные из индикатора, вот так:

double FOR1 = iCustom(NULL,0,"DT-ZigZag-lauer",5,240,0,0);

в результате получаю значения переменной FOR1 при тестировании одни, а при присоединении индикатора в режиме теста его значения другие и даже если совпадают то такое впечатление что это другой таймфрейм, но и то я подобрать его при тестировании не смог.


Да кстати забыл сказать с другими индикаторами до этого таких проблем не было
 
   while(i>0)
   {
      if (iCustom(NULL,TF1,"ZigZag",ExtDepth1,ExtDeviation1,ExtBackstep1,0,i)>0)
      //или iCustom(NULL,TF1,"ZigZag",ExtDepth1,ExtDeviation1,ExtBackstep1,0,i)!=EMPTY_VALUE      
      {
         ExtMapBuffer1[i]=iCustom(NULL,TF1,"ZigZag",ExtDepth1,ExtDeviation1,ExtBackstep1,0,i);
      }
      i--;
   }
 

почитайте: https://www.mql5.com/ru/articles/1490

и поиском по форуму

 
IgorM:

почитайте: https://www.mql5.com/ru/articles/1490

и поиском по форуму


Я понял Ваш намек, что причиной может быть использование значение текущего тика, но предыдущие ведут себя также
 
Проверьте совпадение внешних переменных индикатора в советнике и и индюка который вы вешаете на график.
 
sanyooooook:


Если я понял правильно вот этот кусок кода индикатора решает ту же задачу:

for (int cnt=bigshift; cnt<(100+bigshift); cnt++)
{
zigzag1=iCustom(NULL,GrossPeriod,"ZigZag",depth,5,3,0,cnt+1);
if ( zigzag1!=0 ) break;
}

 
khorosh:
Проверьте совпадение внешних переменных индикатора в советнике и и индюка который вы вешаете на график.

double FOR1 = iCustom(NULL,0,"DT-ZigZag-lauer",5,240,0,0); я даже прописал их в функции результат тот же.

И если это проблема может возникать из-за тестера стратегий, то может научите получать значения присоединённого индикатора в реальном режиме другим способом, например через глобальные переменные (хотя в них я так и не разобрался). Откликнитесь кто-нибудь!!!

 
ingenermig:

double FOR1 = iCustom(NULL,0,"DT-ZigZag-lauer",5,240,0,0); я даже прописал их в функции результат тот же.

И если это проблема может возникать из-за тестера стратегий, то может научите получать значения присоединённого индикатора в реальном режиме другим способом, например через глобальные переменные (хотя в них я так и не разобрался). Откликнитесь кто-нибудь!!!

Индикатор DT-ZigZag-lauer использует данные со старшего ТФ. Если набросить его в тестере на график в режиме визуализации, то он будет заглядывать в будущее старшего ТФ, это известная фича тестера. Советник через iCustom получает правильные данные, без заглядывания в будущее, отсюда и разница в значениях. Верить можно только iCustom'у и советнику.
 
ingenermig:

Подскажите кто может (бьюсь несколько дней) почему при вызове данных индикатора с помощью функции iCustom я получаю данные не такие, какие выводит индикатор при присоединении к графику во время работы с тестером стратегий.


Я даже не читал Ваш код, расскажу свой опыт именно в таком сочетании декораций. Когда я в тестере запускал советник и параллельно с ним индикатор, в котором вызываются данные баров младшего таймфрейма, то при запросе нулевого бара младшего таймфрейма ( а тестер начинает работу с исторических данных, когда нулевой бар в тестировании совершенно не соответствует нулевому бару запрашиваемого таймфрейма. Отсюда валят все косяки. Т.е., в режиме тестирования при запросе, например, нулевого бара с младшего таймфрейма, у меня он выдает значение индикатора именно с настоящего нулевого бара (особенно, если в данный момент терминал подключен к серваку, и идет подкачка истории - на младшем таймфрейме при запросе значения индюка с нулевого бара получится именно текущее значение, но никак не значение, равное нулевому бару в режиме тестирования - надо включать поиск по открытию этого бара, находить смещение и вызывать значение индикатора, но нельзя забывать, что у нулевого бара в режиме тестирования идет переменное значение, а если вызвать его по смещению - мы получим уже будущее - т.е. бар еще не закрыт. а мы уже знаем значения индюка при его закрытии. Поэтому можно брать только показания индюка по 1-му бару тестерного графика (и до него) с рассчитанным смещением, а текущее значение надо рассчитать формулами индюка, но в теле эксперта (или индюка, рассчитанного на присоединение к графику старшего таймфрейма, но показывающего значения младшего). Думаю, Вы меня поняли.

З.Ы. Если не поняли, используйте функцию: while(НЕ ПОНЯЛ!) перечитать;

 
PPC:


Я даже не читал Ваш код, расскажу свой опыт именно в таком сочетании декораций. Когда я в тестере запускал советник и параллельно с ним индикатор, в котором вызываются данные баров младшего таймфрейма, то при запросе нулевого бара младшего таймфрейма ( а тестер начинает работу с исторических данных, когда нулевой бар в тестировании совершенно не соответствует нулевому бару запрашиваемого таймфрейма. Отсюда валят все косяки. Т.е., в режиме тестирования при запросе, например, нулевого бара с младшего таймфрейма, у меня он выдает значение индикатора именно с настоящего нулевого бара (особенно, если в данный момент терминал подключен к серваку, и идет подкачка истории - на младшем таймфрейме при запросе значения индюка с нулевого бара получится именно текущее значение, но никак не значение, равное нулевому бару в режиме тестирования - надо включать поиск по открытию этого бара, находить смещение и вызывать значение индикатора, но нельзя забывать, что у нулевого бара в режиме тестирования идет переменное значение, а если вызвать его по смещению - мы получим уже будущее - т.е. бар еще не закрыт. а мы уже знаем значения индюка при его закрытии. Поэтому можно брать только показания индюка по 1-му бару тестерного графика (и до него) с рассчитанным смещением, а текущее значение надо рассчитать формулами индюка, но в теле эксперта (или индюка, рассчитанного на присоединение к графику старшего таймфрейма, но показывающего значения младшего). Думаю, Вы меня поняли.

З.Ы. Если не поняли, используйте функцию: while(НЕ ПОНЯЛ!) перечитать;


Всё въехал, огромное спасибо за информацию, я думаю она будет интересна всем тем кто после меня столкнётся с такой проблемой.
Причина обращения: