Аналог iBarShift - страница 6

 
Vasiliy Pushkaryov:

TimeCurrent() просто как частный случай под руку попался.

Сейчас более внимательно прочитал вот это примечание к функции Bars():

"При запросе количества баров в заданном диапазоне дат учитываются только те бары, чье время открытия попадает в этот диапазон. Например, если текущий день недели — суббота, то при запросе количества недельных баров с указанием start_time=последний_вторник и stop_time=последняя_пятница функция вернет 0, так как время открытия на недельном таймфрейме всегда приходится на воскресенье, и ни один недельный бар не попадает в указанный диапазон."

Так как время TimeCurrent() почти все время позже времени открытия текущего бара, поэтому функция Bars() возвращает 0. Получается, если мы передадим в качестве параметра start_time время, соответствующее 02:05 на часовом ТФ, и хотим, чтобы нам засчитали бар, начавшийся в 2 часа, тогда нужно получить время открытия бара (02:00:00) через CopyTime(). Иначе функция Bars() этот бар проигнорирует.

Т.е. если сейчас время 3:30, я понимаю, что на часовом ТФ, время 2:05 относится к бару с индексом 1. Этот индекс не вернет ни одна из функций со 2-й страницы. Вот с такой поправкой функция Renat Akhtyamov вернула, то что я ожидал.

Прикладываю скрипт, с 4-мя вариантами функций по поиску индекса, который использовал в качестве теста.

Попробовал представленную функцию, оказалось, что она врёт на один бар, если запрашивается бар с временем, которого нет на чарте. Т.е. если хотим узнать первый бар дня, и запрашиваем по времени  "28.03.2018 00:00" , а бара с таким временем нет, то получим индекс последнего бара прошлого дня.

Или это так и было задумано?

 
Aleksey Vyazmikin:

Попробовал представленную функцию, оказалось, что она врёт на один бар, если запрашивается бар с временем, которого нет на чарте. Т.е. если хотим узнать первый бар дня, и запрашиваем по времени  "28.03.2018 00:00" , а бара с таким временем нет, то получим индекс последнего бара прошлого дня.

Или это так и было задумано?

как передаете время, строкой?
 
Renat Akhtyamov:
как передаете время, строкой?

И строкой пробовал, и так как в ранее выложенном коде.

int teset_01=iBarShift(_Symbol,PERIOD_CURRENT,StringToTime("30.03.2018 00:00"),false);
Print ("teset_01=",teset_01);
 
Aleksey Vyazmikin:

И строкой пробовал, и так как в ранее выложенном коде.

у него же

int iBarShift2(string symbol, ENUM_TIMEFRAMES timeframe, datetime time)

поэтому наличие false не совсем понятно

а если так:

int teset_01=iBarShift2(_Symbol,PERIOD_CURRENT,StringToTime("30.03.2018 00:00"));
Print ("teset_01=",teset_01);
?
 

Пока остановился на таком коде, вроде как быстро отрабатывает:

//+------------------------------------------------------------------+ 
//| Получим iBarShift для заданного номера бара                      | 
//+------------------------------------------------------------------+    
int iBarShift3(const string Symb,const ENUM_TIMEFRAMES TimeFrame,datetime time,const bool Exact=false)
  {
   static int Res=-1;
   static string LastSymb=NULL;
   static ENUM_TIMEFRAMES LastTimeFrame=0;
   static datetime LastTime=0;
   static bool LastExact=false;
   static int PerSec=::PeriodSeconds(LastTimeFrame);
   
   if (LastTimeFrame!=TimeFrame) PerSec=::PeriodSeconds(TimeFrame);
   time-=time%PerSec;

   if((time!=LastTime) || (Symb!=LastSymb) || (TimeFrame!=LastTimeFrame) || (Exact!=LastExact))
     {
      Res=::Bars(Symb,TimeFrame,time,UINT_MAX)-1;
      if(Res<0) Res=0;

      LastTime = time;
      LastSymb = Symb;
      LastTimeFrame=TimeFrame;
      LastExact=Exact;
     }

   return(Res);
  }  

Никто не выявил в этом коде недостатков, или есть более быстрый вариант?

А, ну единственный минус, это если делать запрос на бар, которого ещё нет на чарте, т.е. с сегодняшним временем например.... может и это можно решить как то? Тут как раз был бы смысл возвращать последний известный бар. Это может быть актуально для работы с алгоритмами, которые работают по текущему времени.

 
Renat Akhtyamov:

у него же

поэтому наличие false не совсем понятно

false  - для стандартизации, ни на что не влияет :) Если честно, то я не знаю, зачем этот false в некоторых функциях вообще нужен?

 
Aleksey Vyazmikin:

Пока остановился на таком коде, вроде как быстро отрабатывает:

Никто не выявил в этом коде недостатков, или есть более быстрый вариант?

А, ну единственный минус, это если делать запрос на бар, которого ещё нет на чарте, т.е. с сегодняшним временем например.... может и это можно решить как то? Тут как раз был бы смысл возвращать последний известный бар. Это может быть актуально для работы с алгоритмами, которые работают по текущему времени.

возвращать не существующий номер бара не есть хорошо

проще вернуть -1

 
Aleksey Vyazmikin:

false  - для стандартизации, ни на что не влияет :) Если честно, то я не знаю, зачем этот false в некоторых функциях вообще нужен?

я там заблудился и являюсь приверженцем простых кодов, без двоеточий
 
Renat Akhtyamov:

возвращать не существующий номер бара не есть хорошо

проще вернуть -1

Да не, надо просто возвращать последний известный бар, т.е. с индексом 0, а сейчас он долго думает, что ему там вернуть.

Вот код, который ошибается на один бар, возвращает верный бар - нулевой.

Или Вы про то, что когда в истории запрашивается бар по времени которого нет? Тогда я считаю, что чаще всего нужно получать бар тот, который ближе всего к нашему времени из тех что есть, а код возвращает в этом случае бар со смещением -1 на истории, но корректно отрабатывает, если нет дальнейшей истории - возвращает быстро нулевой бар.

 
Aleksey Vyazmikin:

Да не, надо просто возвращать последний известный бар, т.е. с индексом 0, а сейчас он долго думает, что ему там вернуть.

Вот код, который ошибается на один бар, возвращает верный бар - нулевой.

Или Вы про то, что когда в истории запрашивается бар по времени которого нет? Тогда я считаю, что чаще всего нужно получать бар тот, который ближе всего к нашему времени из тех что есть, а код возвращает в этом случае бар со смещением -1 на истории, но корректно отрабатывает, если нет дальнейшей истории - возвращает быстро нулевой бар.

Да (выделено)

-1 - это единица с минусом (уточняюсь), возвращенная функцией ошибка, которая говорит о том, что такого бара нет

То есть моя функция

Форум по трейдингу, автоматическим торговым системам и тестированию торговых стратегий

Аналог iBarShift

Renat Akhtyamov, 2017.06.08 01:19

Ну и так тоже можно

int iBarShift(string symbol, ENUM_TIMEFRAMES timeframe, datetime tm)
   {
        datetime tm0[1];      
        CopyTime(symbol,timeframe,0,1,tm0);
        int res=Bars(symbol,timeframe,tm0[0],tm)-1;
        return(res);
   }

также требует доработки

хотяяяяя...

Документация:

"Примечание

Если данные для таймсерии с указанными параметрами при вызове функции Bars() еще не сформированы в терминале, или данные таймсерии в момент вызова функции не синхронизированы с торговым сервером, то функция вернет нулевое значение."

====

Если  res==0, то мы итак поймаем от функции -1.

===

Так что все работает, пользуйтесь на здоровье!

Причина обращения: