!IsStopped() в пользовательских индикаторах

 

из обсуждения https://www.mql5.com/ru/forum/196

возник вопрос: насколько оправдано использование  !IsStopped() в циклах расчета пользовательского индикатора, последние по дате индикаторы в кодобазе содержат конструкцию вида:

for(bar=limit; bar>=0 && !IsStopped(); bar--)

безусловно, чем больше проверок тем отказоустойчивее код, опубликованные статьи, к примеру https://www.mql5.com/ru/articles/35 ,не содержат примеров с использованием  IsStopped() , возможно ли некорректное исполнение кода  пользовательского индикатора без  IsStopped() ? Насколько оправдано использование " for(bar=limit; bar>=0 && !IsStopped(); bar--) " именно в таком виде?

ЗЫ:если не ошибаюсь, то циклы for() обычно предназначены для максимально быстрого выполнения тела итерации, для циклов с проверкой множественных условий логичнее использовать while()

ЗЫЗЫ:  подозреваю, что в индикаторах использующих сложные математические вычисления добавление  IsStopped() даст дополнительное "притормаживание" , а может и поможет корректно завершить код индикатора через OnDeinit()

Индикаторы: Bulls Power
Индикаторы: Bulls Power
  • www.mql5.com
Данный индикатор лучше всего использовать в совокупности с одним из трендовых индикаторов (чаще всего это скользящая средняя):.
 

Было бы интересно узнать об истории происхождения этого !IsStopped() в цикле индикатора из первых уст. Зачем?

Не нужен он. 

 
Integer:Не нужен он. 
имхо,  !IsStopped() логичен если нужно вызвать и обработать OnDeinit() , но не знаю как при вызове   IsStopped()   ведет себя  OnDeinit() , наверное есть временные ограничения на аварийное завершение программы
 
IgorM:
имхо,  !IsStopped() логичен если нужно вызвать и обработать OnDeinit() , но не знаю как при вызове   IsStopped()   ведет себя  OnDeinit() , наверное есть временные ограничения на аварийное завершение программы
В деините уже поздно. Он может быть только полезен, если прицепил индикатор, и тут же торкнуло его снять. Должно очень бысто торкать, такого не бывает.
 
Integer: В деините уже поздно. 

набросал такой индикатор:

#property indicator_separate_window
#property indicator_buffers 1
#property indicator_plots   1
//--- plot Label1
#property indicator_label1  "Label1"
#property indicator_type1   DRAW_LINE
#property indicator_color1  clrRed
#property indicator_style1  STYLE_SOLID
#property indicator_width1  1

input int testcount = 1000;
//--- indicator buffers
double         Label1Buffer[];
int OnInit(){
SetIndexBuffer(0,Label1Buffer,INDICATOR_DATA);
return(0);
}
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
                const int prev_calculated,
                const int begin,
                const double &price[])
  {
   int i,j,start;
   uint tickCount;
   if(prev_calculated==0) start=0; else start=prev_calculated-1;
   tickCount = GetTickCount();
   for(j =0; j<testcount;j++){
         for(i=start;i<rates_total && !IsStopped();i++){
            Label1Buffer[i] = price[i];
         }
   }
   tickCount = GetTickCount() - tickCount;
   Print("время выполнения = ",tickCount);
  return(rates_total);
  }
//+------------------------------------------------------------------+
void OnDeinit(const int reason){
   Print("код причины деинициализации = ",reason);
}
первый раз запустил без  !IsStopped() затем правой мышью... удалил индикатор - ничего не обычного, попробовал те же манипуляции с  !IsStopped() терминал подвис на несколько секунд, возможно косяки с моей стороны - ноут уже не самый быстрый (Win7 - 32bit), а может из-за  !IsStopped()  притормаживает?
 
IgorM:

ЗЫЗЫ:  подозреваю, что в индикаторах использующих сложные математические вычисления добавление  IsStopped() даст дополнительное "притормаживание" , а может и поможет корректно завершить код индикатора через OnDeinit()

Не нужно на каждой итерации проверять этот флаг.

Можно проверять раз в 1000 циклов или больше - все зависит от конкретного случая.

 
IgorM:

набросал такой индикатор:

...
В первом случае наверно была длинная пауза от присоединения индикатора до снятия и он успел закончить все циклы, а во втором может быть была короткая пауза, в цикле  for(j =0; j<testcount;j++) нет IsStopped() ждали пока он завершится. 
Документация по MQL5: Операции с графиками / ChartIndicatorAdd
Документация по MQL5: Операции с графиками / ChartIndicatorAdd
  • www.mql5.com
Операции с графиками / ChartIndicatorAdd - Документация по MQL5
 
Renat:

Не нужно на каждой итерации проверять этот флаг.

Можно проверять раз в 1000 циклов или больше - все зависит от конкретного случая.

Ренат, подскажите если знаете, зачем тогда в большинстве индикаторов в CodeBase написаных MetaQuotes присутствует !IsStopped() в цикле for?
 
paladin800:Ренат, подскажите если знаете, зачем тогда в большинстве индикаторов в CodeBase написаных MetaQuotes присутствует !IsStopped() в цикле for?

подозреваю, что это не проверенная "перестраховка" программистов, я же писал Вам в параллельном топике - в более ранних индикаторах такого не было, кстати в кодебазе авторы не только MetaQuotes , любой желающий может опубликовать свой код

если люди, чью компетентность не вызывает сомнения, сказали что не нужно, на том и порешим -  

for(bar=limit; bar>=0 && !IsStopped(); bar--) // не правильно

for(bar=limit; bar>=0 ; bar--)  // правильно 

Integer:
В первом случае наверно была длинная пауза от присоединения индикатора до снятия и он успел закончить все циклы, а во втором может быть была короткая пауза, в цикле  for(j =0; j<testcount;j++) нет IsStopped() ждали пока он завершится. 

логично, издалека виден "профессиональный нюх" на работу программы изнутри ;)

 

спасибо! 

 
paladin800:Ренат, подскажите если знаете, зачем тогда в большинстве индикаторов в CodeBase написаных MetaQuotes присутствует !IsStopped() в цикле for?

хм, поиском https://www.mql5.com/ru/search#!author=metaquotes&module=mql5_module_codebase

просмотрел выборочно результаты, действительно у автора   MetaQuotes используется    !IsStopped() в цикле for

даже не могу прокомментировать эту ситуацию 

 

Представил себе такую ситуацию. Напр. кто-то включил 10 терминалов, на каждом по 50 графиков, а на каждом графике по 4 индикатора получается работает 2000 индикаторов, то торможение из-за !IsStopped() уже ощутимо. Если убрать, то при итерации 100.000 (столько по умолчанию в терминале отображается баров в окне), когда выключить терминал то он может подвиснуть ожидая окончания итераций.

Начертил такой вот код для проверки на каждой 10.000 итерации чтоб приемлимо работало в обоих ситуациях.

//--- main loop of calculations
   int stop=10000;
   for(i=limit; i<rates_total; i++)
     {
      // вычисления
      if (i==stop)
        {
         if (!IsStopped()) stop=stop+10000;
         else return(0);
        }
     }
Причина обращения: