Особенности языка mql5, тонкости и приёмы работы - страница 111

 
pavlick_:

 ...

Пользуйтесь пожалуйста встроенным форматированием текста - над полем ввода сообщения есть меню - там есть всё. И горячие клавиши тоже там описаны.

Я ваши "quote" исправил.

 
pavlick_:

Как это так же? Там автоматом имеется копирующий конструктор и все манипуляции будут иметь вид:

... 
ar.Add(new(q));


Как я понимаю, имелось ввиду new Q(q).  Теперь понятно, что речь шла об отсутствии автоматического конструктора копирования в MQL.

 
Задача

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

Ошибки, баги, вопросы

fxsaber, 2018.12.21 10:23

Не могу сообразить, прошу подсказать. Есть такое получение времени

int GetHandle() { return(0); }

bool SelectHandle( int ) { return(true); }
  
int NewHandle = 0;  
int PrevHandle = GetHandle();    

datetime time = SelectHandle(NewHandle) ? TimeCurrent() : 0;  
SelectHandle(PrevHandle);


Как написать макрос, делающий то же самое

time = MACROS(NewHandle, TimeCurrent()); // Макрос


Проблема в том, что PrevHandle в макросе не создать.

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

Ошибки, баги, вопросы

fxsaber, 2018.12.21 22:15

Уточню, что NewHandle - может быть константой. Т.е. валидный такой вызов
time = MACROS(0, TimeCurrent()); // TimeCurrent из 0-хендла.
time = MACROS(1, TimeCurrent()); // TimeCurrent из 1-хендла.

MACROS(0, SymbolInfoTick(_Symbol, Tick)); // SymbolInfoTick из 0-хендла.

#define Bid SymbolInfoDouble(_Symbol, SYMBOL_BID)
Price = MACROS(3, Bid); // Bid из 3-хендла.


Решение

template <typename T>
T Memory( const T NewValue, const bool SetFlag = true )
{
  static T PrevValue;
  
  if (SetFlag)
    PrevValue = NewValue;
 
  return(PrevValue); 
}

template <typename T1, typename T2>
T2 MacrosFunc( const T1, const T2 Value, const T1 )
{
  return(Value);
}

#define MACROS(A, B) MacrosFunc(SelectHandle(Memory(A, false)), B, SelectHandle(Memory(A)))


 
fxsaber:

Решение

...
template <typename T1, typename T2>
T2 MacrosFunc( const T1, const T2 Value, const T1 )
{
  return(Value);
}

#define MACROS(A, B) MacrosFunc(SelectHandle(Memory(A, false)), B, SelectHandle(Memory(A)))


У вас выражение B будет всегда вычисляться и возвращаться, независимо от остального.

 
Alexey Navoykov:

У вас выражение B будет всегда вычисляться и возвращаться, независимо от остального.

Там последовательное (справа-налево) вычисление входных параметров вспомогательных функций.

 
fxsaber:

Там последовательное (справа-налево) вычисление входных параметров вспомогательных функций.

Что это меняет?  Макрос всегда возвращает значение B
 
Alexey Navoykov:
Что это меняет?  Макрос всегда возвращает значение B

Попробуйте опровергнуть решение. Ошибки не вижу.


Сначала переключается на NewHandle, затем берется B, после чего переключается на предыдущий хэндл.

 
fxsaber:

Сначала переключается на NewHandle, затем берется B, после чего переключается на предыдущий хэндл.

А исходная задача была такая:

SelectHandle(NewHandle) ? TimeCurrent() : 0; SelectHandle(PrevHandle);

Т.е. должно выполниться условие
 
Alexey Navoykov:

А исходная задача была такая:

Так то же самое

template <typename T1, typename T2>
T2 MacrosFunc( const T1 NewHandle, const T2 Value )
{
  return(Value);
}

#define MACROS(A, B) MacrosFunc(SelectHandle(Memory(A, false)), SelectHandle(Memory(A)) ? B : 0)


После давал комментарий, который задачу несколько обобщил - там и SymbolInfoTick и SymbolInfoDouble и т.д.

 

Кстати я пришёл к выводу, что в общем случае, если тип возвращаемого значения функции будет абсолютно любым, то задача не решаема средствами MQL.  Требуется decltype, которого здесь нет.

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