Помогите найти ошибку

 
//+------------------------------------------------------------------+ //| IBS.mq4 | //| Maks Skam™ | //| mailto:******@****** | //+------------------------------------------------------------------+ #include <stdlib.mqh> #property copyright "Maks Skam™" #property link "******@******" #property indicator_separate_window #property indicator_minimum 0 #property indicator_maximum 100 #property indicator_buffers 1 #property indicator_color1 Yellow extern int IBSPeriod = 5; //Количество исторических баров double IBSBuffer[]; int init() { string ShortName; IndicatorBuffers(1); SetIndexStyle(0,DRAW_LINE); SetIndexBuffer(0,IBSBuffer); ShortName="IBS("+IBSPeriod+")"; IndicatorShortName(ShortName); SetIndexLabel(0,ShortName); SetIndexDrawBegin(0,IBSPeriod); return(0); } int start() { int i, err; int counted_bars = IndicatorCounted(); double BS; if(Bars <= IBSPeriod){ Alert("Ошибка: Баров меньше, чем период [Баров: " + Bars + ", а период: " + IBSPeriod + "]!"); return(0); } if(counted_bars < 0) return(-1); if(counted_bars > 1) for(i=1;i<=IBSPeriod;i++) IBSBuffer[Bars-i]=0.0; i = Bars-IBSPeriod-1; if(counted_bars >= IBSPeriod) i=Bars-counted_bars-1; while(i>=0) { /********МАТЕМАТИКА СИЛЫ БАРА ************************/ BS = 0; for(int k=0; k < IBSPeriod; k++) BS += MathAbs(Low[i-k]-Close[i-k])/(High[i-k] - Low[i-k]); IBSBuffer[i]=BS*100/IBSPeriod; /***************************************************/ i--; } return(0); }


Вот такой индикаторик. Работает каласо, но единственное, в чем его глюк - так это в том, что график этого индикатора недорисовывает первые IBSPeriod точек (в данном случае 5). Т.е. как бы отстает на 5 значений... Не понимаю где загвоздка...
 
MaksSkam:



Вот такой индикаторик. Работает каласо, но единственное, в чем его глюк - так это в том, что график этого индикатора недорисовывает первые IBSPeriod точек (в данном случае 5). Т.е. как бы отстает на 5 значений... Не понимаю где загвоздка...
На первый взгляд:
while(i>=0) { //********МАТЕМАТИКА СИЛЫ БАРА ************************ BS = 0; for(int k=0; k < IBSPeriod; k++) if(!bCompareDouble(High[i+k] - Low[i+k],0.0)) BS += MathAbs(Low[i+k]-Close[i+k])/(High[i+k] - Low[i+k]); IBSBuffer[i]=BS*100/IBSPeriod; //*************************************************** i--; } return(0); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool bCompareDouble (double dNumber1, double dNumber2) { bool bCompare= NormalizeDouble(dNumber1 - dNumber2,8) == 0; return(bCompare); }
 
Editor:
MaksSkam:



Вот такой индикаторик. Работает каласо, но единственное, в чем его глюк - так это в том, что график этого индикатора недорисовывает первые IBSPeriod точек (в данном случае 5). Т.е. как бы отстает на 5 значений... Не понимаю где загвоздка...
На первый взгляд:
while(i>=0) { //********МАТЕМАТИКА СИЛЫ БАРА ************************ BS = 0; for(int k=0; k < IBSPeriod; k++) if(!bCompareDouble(High[i+k] - Low[i+k],0.0)) BS += MathAbs(Low[i+k]-Close[i+k])/(High[i+k] - Low[i+k]); IBSBuffer[i]=BS*100/IBSPeriod; //*************************************************** i--; } return(0); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool bCompareDouble (double dNumber1, double dNumber2) { bool bCompare= NormalizeDouble(dNumber1 - dNumber2,8) == 0; return(bCompare); }
Т.е., по сути, необходимо обрабатывать ситауцию нуль-бара, т.е. когда High = Low (=Open=Close) ?
 
MaksSkam:


Т.е., по сути, необходимо обрабатывать ситауцию нуль-бара, т.е. когда High = Low (=Open=Close) ?
Надо проверять деление на 0.
В редакторе MetaEditor <меню Вид-Навигатор-вкладка Словарь-Выполнение программ-Ошибки выполнения> написано:

Существует ряд критических ошибок, при возникновении которых выполнение программы немедленно прерывается:
ERR_REMAINDER_FROM_ZERO_DIVIDE ( 4012) - Деление на 0 при взятии остатка от деления.
ERR_ZERO_DIVIDE (4013) - Деление на 0.

Кроме того, надо правильно индексировать бары:
 
C индексацией понятно — спасибо
А вот с деление все же не очень... Я правильно понимаю, что в знаменателе может быть ноль <=> High[i-k] = Low[i-k] <=> бара по сути нет...
 
MaksSkam:
C индексацией понятно — спасибо
А вот с деление все же не очень... Я правильно понимаю, что в знаменателе может быть ноль <=> High[i-k] = Low[i-k] <=> бара по сути нет...
После первого же деления на ноль исполнение MQL-программы прерывается, расчеты и отрисовка индикатора прекращается, то есть на графике ничего не рисуется.
 
MaksSkam:

А вот с деление все же не очень...
Нельзя делить на ноль - получается стремление к бесконечности. Вот и поэтому если на любом комп. языке появиться что-то/0 то возникает ошибка. Так что эта ситуация требует специальная обработка.
 
Про ноль понятно. Я понимаю, что деление на ноль сразу вызывает завершение программы без отрисовки графиков и всех дел, и что эту ситуацию нужно обрабатывать, это все понятно.
Вопрос в том, а что это за ситуация такая, когда произойдет деление на ноль?
 
MaksSkam:
Про ноль понятно. Я понимаю, что деление на ноль сразу вызывает завершение программы без отрисовки графиков и всех дел, и что эту ситуацию нужно обрабатывать, это все понятно.
Вопрос в том, а что это за ситуация такая, когда произойдет деление на ноль?
А вот здесь: /(High[i+k] - Low[i+k]) ?
Что произойдет, если бар будет представлять собой додж, у которого low=high?
 
Renat:
MaksSkam:
Про ноль понятно. Я понимаю, что деление на ноль сразу вызывает завершение программы без отрисовки графиков и всех дел, и что эту ситуацию нужно обрабатывать, это все понятно.
Вопрос в том, а что это за ситуация такая, когда произойдет деление на ноль?
А вот здесь: /(High[i+k] - Low[i+k]) ?
Что произойдет, если бар будет представлять собой додж, у которого low=high?
О! Вот это-=то я и хотел услышать...
А что такое додж?
Такое вообще возможно? Получается, что по сути бара вообще нет. ..
 
Бар есть, нет движения за этот интервал времени. Бар открыля, да так и остался неизменным, был всего один тик (Volum[i]=1). На фьючерсах таких фокусы бывают даже на дневках.