что может заставлять индикатор пересчитываться...?
RefreshRates () используете?
( в mql5 Refresh() )
Я написал индикатор, который рисует 8 баров рядом с последними барами обычного графика цен.
Этот индикатор использует другой индикатор (тоже самодельный) (и не очень быстрый) (Типа ATR).
Когда я присоединяю этот MyATR индикатор к графику цен, он ведёт себя нормально: в начале проходит по всем барам, потом только последний бар пересчитывает.
Но если я его вызываю из первого упомянутого индикатора, то он каждый тик пересчитывает все бары графика.
В результате получаю сильное торможение.
=============================================
Подскажите, пожалуйста, что может заставлять индикатор пересчитываться когда он запущен в потоке другого индикатора?
С кодом было бы по-проще. Но, я бы предположил, что где-то в вашем индикаторе в OnCalculate() есть строка return( 0 ); Это означает, что происходит полный пересчет текущего индикатора, а раз он использует MyATR, то задействует и его данные на всей истории.
Второй вариант: Ваш индикатор (рисующий 8 баров) достаточно медленный. И MyATR достаточно медленный. В совокупности - все крайне медленно.
Да, а с чего Вы взяли, что пересчитываются все бары MyATR?
Я написал индикатор, который рисует 8 баров рядом с последними барами обычного графика цен.
Этот индикатор использует другой индикатор (тоже самодельный) (и не очень быстрый) (Типа ATR).
Когда я присоединяю этот MyATR индикатор к графику цен, он ведёт себя нормально: в начале проходит по всем барам, потом только последний бар пересчитывает.
Но если я его вызываю из первого упомянутого индикатора, то он каждый тик пересчитывает все бары графика.
В результате получаю сильное торможение.
=============================================
Подскажите, пожалуйста, что может заставлять индикатор пересчитываться когда он запущен в потоке другого индикатора?
С кодом было бы по-проще. Но, я бы предположил, что где-то в вашем индикаторе в OnCalculate() есть строка return( 0 ); Это означает, что происходит полный пересчет текущего индикатора, а раз он использует MyATR, то задействует и его данные на всей истории.
Второй вариант: Ваш индикатор (рисующий 8 баров) достаточно медленный. И MyATR достаточно медленный. В совокупности - все крайне медленно.
Да, а с чего Вы взяли, что пересчитываются все бары MyATR?
1. Вот функция start вызываемого индикатора я его в первом посте условно назвал MyATR. Где GuestSmb - это один из инпутов. SMB - символ к которому присоединён индикатор, TF-общий таймфрейм
int start() { int counter, counterBars, counted_bars=IndicatorCounted(); int shortestBars = MathMin(Bars, iBars(GuestSmb, TF))-1; int k,i,limit=shortestBars; if(shortestBars < InpAtrPeriod + 12) return(0); if ( counted_bars > 0 ) limit=shortestBars-counted_bars+2; if ( counted_bars <= 0 ) limit=shortestBars; if(Bars<=InpAtrPeriod || InpAtrPeriod<=0) return(0); if(true) { ExtTRBuffer[0]=0.0; counterBars=0; for(k=limit; k>0; k--) { datetime guestDateTime = iTime(GuestSmb, TF, k); i = iBarShift(SMB, TF, guestDateTime, false); datetime guestDateTime2 = iTime(GuestSmb, TF, k+1); int i2 = iBarShift(SMB, TF, guestDateTime2, false); if(i == -1 || i2 == -1 || iClose(GuestSmb, TF, k+1) == 0 || i+1 != i2) { ExtTRBuffer[k] = EMPTY_VALUE; continue; } counterBars++; if(i < 1) break; double guest; if(InpAtrReverse) { guest = MathMax(1.0/iLow(GuestSmb, TF, k),1.0/iClose(GuestSmb, TF, k+1)) - MathMin(1.0/iHigh(GuestSmb, TF, k),1.0/iClose(GuestSmb, TF, k+1)); } else { guest = MathMax(iHigh(GuestSmb, TF, k),iClose(GuestSmb, TF, k+1)) - MathMin(iLow(GuestSmb, TF, k),iClose(GuestSmb, TF, k+1)); } double native = MathMax(High[i],Close[i2])-MathMin(Low[i],Close[i2]); if(native != 0) ExtTRBuffer[k]=guest/native; else ExtTRBuffer[k]=EMPTY_VALUE; } int secondCycleLimit = limit-InpAtrPeriod; if(secondCycleLimit < 2) secondCycleLimit = 2; bool calculationDone = false; for(k=1; k<secondCycleLimit; k++) { double firstValue=0.0; ExtATRBuffer[k]=0.0; counter=0; int foundCounter = 0; for(i=1; foundCounter<=InpAtrPeriod; i++) { int barShift = k+i+counter; if(barShift > shortestBars) calculationDone = true; // // secondCycleLimit if(calculationDone) break; if(ExtTRBuffer[barShift] == EMPTY_VALUE) { counter++; continue; } foundCounter++; firstValue+=ExtTRBuffer[barShift]; } if(calculationDone) break; firstValue/=InpAtrPeriod; ExtATRBuffer[k]=firstValue; } }
2. В случае полного пересчёта, внешний индикатор перечитывает только 8 баров (поскольку MaxBars = 8). Вот и его код:
int start() { int counted_bars=IndicatorCounted(); int shortestBars = MathMin(Bars, iBars(symbol, TF))-1; int k,i,limit=shortestBars; if(shortestBars < ScalePeriod + 12) return(0); limit = MaxBars; //--- check for bars count and input parameter if(Bars<=ScalePeriod || ScalePeriod<=0) return(0); //============================================= if(true) { // counted_bars==0 for(k=limit; k>1; k--) { datetime hostDateTime = iTime(SMB, TF, k); i = iBarShift(symbol, TF, hostDateTime, false); if(i == -1) { ExtLowHighBuffer[k] = EMPTY_VALUE; ExtHighLowBuffer[k] = EMPTY_VALUE; ExtOpenBuffer[k] = EMPTY_VALUE; ExtCloseBuffer[k] = EMPTY_VALUE; continue; } ScaleData2 sd = MakeScaleCoeff3(symbol, DoRevese, ScalePeriod, k) ; ScaledBar b = ScaleOneBar2(Time[k], symbol, sd, DoRevese) ; if(b.o < b.c) { ExtLowHighBuffer[k] = b.l; ExtHighLowBuffer[k] = b.h; } else { ExtLowHighBuffer[k] = b.h; ExtHighLowBuffer[k] = b.l; } ExtOpenBuffer[k] = b.o; ExtCloseBuffer[k] = b.c; } } return(0); }
это вроде не должно приводить к полному пересчёту вызываемого индикатора, поскольку функция MakeScaleCoef3 читает значения индикатора MyATR только с нескольких последних баров. Или я тут что-то неправильно понимаю?
3. Он пересчитывает все бары, потому что я добавлял Print(BarNumber). Если присоединяю индикатор MyATR к графику, то он только один раз проходится по всем барам, а если MyATR вызывается внешним индикатором, то Print на каждом тике выводит мне полный список баров.
RefreshRates () используете?
( в mql5 Refresh() )
Нет не использую. Но всё равно спасибо!
Вам говорили, что у вас красивая фотка?
Попробуйте в расчете первого индикатора считать только нужное кол-во баров назад, то есть 2 или 3 или сколько надо а не по всей истории
Вообще-то у меня план нарисовать индикатор по всей истории. Это я сейчас ограничился 8 барами, чтобы компьютер не подвисал.
Но я хотел в итоге добиться того, чтобы первый индикатор просчитал всю историю, потом второй, используя буфер первого, просчитал всю историю, а дальше только считали бы новые бары.
1. Вот функция start вызываемого индикатора я его в первом посте условно назвал MyATR. Где GuestSmb - это один из инпутов. SMB - символ к которому присоединён индикатор, TF-общий таймфрейм
2. В случае полного пересчёта, внешний индикатор перечитывает только 8 баров (поскольку MaxBars = 8). Вот и его код:
это вроде не должно приводить к полному пересчёту вызываемого индикатора, поскольку функция MakeScaleCoef3 читает значения индикатора MyATR только с нескольких последних баров. Или я тут что-то неправильно понимаю?
3. Он пересчитывает все бары, потому что я добавлял Print(BarNumber). Если присоединяю индикатор MyATR к графику, то он только один раз проходится по всем барам, а если MyATR вызывается внешним индикатором, то Print на каждом тике выводит мне полный список баров.
MakeScaleCoef3() тоже покажите. В приведенном коде я ошибок полного пересчета не увидел (что не обязательно означает, что их там нет)).
3. Коли так, то дело, скорее всего и есть в функции MakeScaleCoef3(), т.к. именно она, если верить Вашим словам, читает значения индикатора MyATR.
MakeScaleCoef3() тоже покажите. В приведенном коде я ошибок полного пересчета не увидел (что не обязательно означает, что их там нет)).
3. Коли так, то дело, скорее всего и есть в функции MakeScaleCoef3(), т.к. именно она, если верить Вашим словам, читает значения индикатора MyATR.
Вот:
ScaleData2 MakeScaleCoeff3(string smb, bool reverse, int barsWind, int barStart) { ScaleData2 s; int i; int lastBar = barStart+barsWind; double avg = 0; double atrRatio = iCustom(smb, TF, "AtrRatio", barsWind, reverse, 0, barStart) ; // iATR(smb, TF, BarsWind, barStart); double coef = atrRatio; // if(reverse) coef = 1*atrHost/atrGuest;// atrGuest/atrHost; // Print(smb, " atrGuest = ", atrGuest, " atrHost = ", atrHost, " coef = ", coef, " reverse = ", reverse); double avgShift = 0; if(reverse) { for(i=barStart; i<lastBar; i++) { avgShift += iOpen(SMB, TF, i) - coef/iOpen(smb, TF, i); avgShift += iClose(SMB, TF, i) - coef/iClose(smb, TF, i); } } else { for(i=barStart; i<lastBar; i++) { avgShift += iOpen(SMB, TF, i) - coef*iOpen(smb, TF, i); avgShift += iClose(SMB, TF, i) - coef*iClose(smb, TF, i); } } avgShift = avgShift/barsWind/2.0; s.coef = coef; s.shift= avgShift; return s; }
Вызывается для одного бара.
Здесь менее всего я ожидаю обнаружить ошибку.
Здесь помочь может только клуб телепатов.
Скорее всего индикатор вызывается с неправильными параметрами.
- Бесплатные приложения для трейдинга
- 8 000+ сигналов для копирования
- Экономические новости для анализа финансовых рынков
Вы принимаете политику сайта и условия использования
Я написал индикатор, который рисует 8 баров рядом с последними барами обычного графика цен.
Этот индикатор использует другой индикатор (тоже самодельный) (и не очень быстрый) (Типа ATR).
Когда я присоединяю этот MyATR индикатор к графику цен, он ведёт себя нормально: в начале проходит по всем барам, потом только последний бар пересчитывает.
Но если я его вызываю из первого упомянутого индикатора, то он каждый тик пересчитывает все бары графика.
В результате получаю сильное торможение.
=============================================
Подскажите, пожалуйста, что может заставлять индикатор пересчитываться когда он запущен в потоке другого индикатора?