Вопросы от начинающих MQL5 MT5 MetaTrader 5 - страница 245

 
forexman77:

В скрипте сделал вот такую штуку:

time=0

SymbolInfoTick  в понедельник проверю 

Проверить можно вот таким кодом:

void OnStart()
{
  double ask;
  uint start=GetTickCount();
  for(int i=0;i<1000000;i++)
  {
    ask=SymbolInfoDouble(Symbol(),SYMBOL_ASK);
  }
  uint time=GetTickCount()-start;
  Print("SymbolInfoDouble = ",time," ms");
  
  MqlTick tick;
  start=GetTickCount();
  for(int i=0;i<1000000;i++)
  {
    SymbolInfoTick(Symbol(),tick);
  }
  time=GetTickCount()-start;
  Print("SymbolInfoTick = ",time," ms");
}

 Но нужны тики по символу.

 
Fleder:

Проверить можно вот таким кодом:

 Но нужны тики по символу.

Да, "SymbolInfoTick", сегодня не проверить.

Пробовал, пока тики не пойдут ничего не получится

void OnStart()
  {
uint start=GetTickCount();
double iask=0;
MqlTick latest_price;       // Будет использоваться для текущих котировок  
if(!SymbolInfoTick(_Symbol,latest_price)){iask=latest_price.ask;}
Alert("iask=",iask);
uint time=GetTickCount()-start;
Alert("time=",time);  
  }
iask=0
 
forexman77:

Да, "SymbolInfoTick", сегодня не проверить.

Пробовал, пока тики не пойдут ничего не получится

iask=0

Эта функция работает слишком быстро.

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

 
barabashkakvn:
Тем более интересно, пример кода есть. Ждем результата.
 
forexman77:
Спасибо. Пригодится.
 

Для проверки нового бара в советнике использовал функции на основе «CopyTime», «CopyRates», что находил на форумах. Пришел к выводу, что их расчет занимает много времени.

Вот данные проверки (примечательно, что вызов индикатора занимает 171 мс):

datetime New_Time[];//буффер для проверки нового бара
void OnStart()
  {
uint start=GetTickCount();
for(int i=0;i<1000000;i++)
{
static datetime t;//записываем старое время  
ArraySetAsSeries(New_Time,true);//направление индексации
CopyTime(_Symbol,_Period,0,1,New_Time);//копируем время нового бара
t=New_Time[0];   
}
uint time=GetTickCount()-start;
Print("New_Time = ",time," ms");
  }

MqlRates rates[]; 
void OnStart()
  {
datetime t;  
uint start=GetTickCount();
for(int i=0;i<1000000;i++)
{
ArraySetAsSeries(rates,true);
int copied=CopyRates(Symbol(),Period(),0,1,rates);  
t=rates[0].time; 
}
uint time=GetTickCount()-start;
Print("t = ",time," ms");
  }

И тут задался мыслью, что если попробовать, что-то другое. Например «TimeCurrent»

Сделал следующий код для оптимизации:

void OnStart()
  {
int t;
int s;  
uint start=GetTickCount();
for(int i=0;i<1000000;i++)
{

MqlDateTime m;
TimeCurrent(m);
t=m.min;
s=m.sec;
}
uint time=GetTickCount()-start;
Print("time = ",time," ms");    
  }

 

Сделал следующий код для оптимизации в советнике:

static double ind1;//записываю значения
static double ind2;// значения
static double indsmall;//индикаторов
MqlDateTime m;
TimeCurrent(m);
int MIN=m.min;
int SEC=m.sec;
if (MIN==0 && SEC==0)//проверка только в начале часа
{
Здесь копирую значения индикатора из буфферов
}

Результат в одиночном прогоне без проверки нового бара, когда значения индикатора получаются на каждом тике: 817 196 мс

С проверкой нового бара:735 904 мс

Разница не особо впечатляет, есть улучшения, но этого мало.

Индикатор получаю следующим образом:

int TSIHandle;   // хэндл индикатора  TSI
double TSI[]; // динамические массивы для хранения численных значений TSI

int OnInit()
  {
TSIHandle=iCustom(NULL,0,"Blau_TSI",q,r,s,u,PRICE_CLOSE);
if(TSIHandle<0){Alert("Ошибка при создании индикаторов - номер ошибки: ",GetLastError(),"!!");return(-1);}
ArraySetAsSeries(TSI,true);
   return(0);
  }

void OnDeinit(const int reason)
  {
//--- освобождаем хэндлы индикаторов
   IndicatorRelease(TSIHandle);
   ArrayFree(TSI);
  }

void OnTick()
  {
MqlDateTime m;
TimeCurrent(m);
int MIN=m.min;
int SEC=m.sec;
static double tsismall;

if (MIN==0 && SEC==0)
{
//--- копируем значения индикаторов из индикаторных буферов
   if(CopyBuffer(TSIHandle,0,0,3,TSI)<0)
     {
      Alert("Ошибка копирования буферов индикатора Moving Average - номер ошибки:",GetLastError(),"!!");
      return;
     }
tsismall=TSI[1];
}
}

Пробовал поместить код с вызовом хендлов в блок где происходит проверка нового бара, выходит ошибка, если в этой строке

if(TSIHandle<0){Alert("Ошибка при создании индикаторов - номер ошибки: ",GetLastError(),"!!");return(-1);}

ставлю, что return ничего не возвращает ошибок нет, но советник не работает.

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

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

 
Кто может подсказать как сделать индикатор по выводу результатов одной лишь формулы  buffer[i] = (1.3747-(MarketInfo("EURUSD", MODE_BID))+0.8835-(MarketInfo("USDCHF", MODE_BID)))*10000;
 
rus-lot:
Кто может подсказать как сделать индикатор по выводу результатов одной лишь формулы  buffer[i] = (1.3747-(MarketInfo("EURUSD", MODE_BID))+0.8835-(MarketInfo("USDCHF", MODE_BID)))*10000;

Вам нужно написать пользовательский индикатор. Для облегчения процесса - взять один из самых простых индикаторов - iMa  и переписать немного. Вот еще тема, где говорится о MarketInfo. Пишите код, спрашивайте, если что не получится. 

 
А что случилось со статическими переменными? Сегодня обновил старый билд терминала и сейчас при компиляции ошибки:

unresolved static variable
 
sgreen:
А что случилось со статическими переменными? Сегодня обновил старый билд терминала и сейчас при компиляции ошибки:

unresolved static variable

Теперь статические члены-данные класса необходимо размещать:

//+------------------------------------------------------------------+
//| Класс "Анализатор текстов"                                       |
//+------------------------------------------------------------------+
class СParser
  {
public:
   static int        s_words;
   static int        s_symbols;
   //--- конструктор и деструктор
                     Parser(void);
                    ~Parser(void){};
  };
...
//--- инициализация статических членов класса Parser на глобальном уровне
int CParser::s_words=0;
int CParser::s_symbols=0;
Причина обращения: