Мультисимвольное виртуальное окружение.

13 декабря 2023, 12:36
fxsaber
0
272

Данный пост посвящен дополнительному функционалу библиотеки виртуального окружения Virtual:


Мультисимвольность.

Теперь можно торговать в VIrtual не по одному символу, а по любым в одном виртуальном окружении. И таких окружений может быть любое количество (ограничения только по памяти). Это позволяет, например, значительно проще создавать копиры с тех же криптобирж. Сценариев применения много. Здесь же остановимся на применении данного функционала в MT5-Тестере.


Тестер.

Для проверки корректности работы мультисимвольного торгового окружения возьмем такой советник (на базе этого).

#include <MT4Orders.mqh> // https://www.mql5.com/ru/code/16006

#define VIRTUAL_TESTER_MULTI // Запуск в виртуальном торговом окружении OnTickMulti
#define VIRTUAL_LIMITS_TP_SLIPPAGE // Лимитники и TP исполняются по первой цене акцепта - положительные проскальзывания
#define VIRTUAL_CLOSEALL_BYEND // Закрывает принудительно все ордера в конце тестирования
#include <fxsaber\OnTickMulti\OnTickMulti.mqh> // https://www.mql5.com/ru/code/47647

#define REPORT_TESTER             // В тестере будут автоматически записываться отчеты
#define REPORT_BROWSER            // Создание отчета с запуском браузера - требует разрешения DLL.
#include <Report.mqh> // https://www.mql5.com/ru/code/18801

// https://www.mql5.com/ru/forum/282062/page46#comment_50705106
input group "EA's inputs"
input int inAmount = 5;
input int inOffset = 5;
input int inRange = 0;

bool OrdersBuy[];
bool OrdersSell[];

void OnInit()
{
  ArrayResize(OrdersBuy, inAmount + 1);
  ArrayResize(OrdersSell, inAmount + 1);
}

// Мультисимвольный OnTick.
void OnTickMulti( const string &Symb, const int &Index )
{
  MqlTick Tick;
  
  if (SymbolInfoTick(Symb, Tick))
  {    
    const double Offset = inOffset * SymbolInfoDouble(Symb, SYMBOL_POINT);

    ArrayInitialize(OrdersBuy, false);
    ArrayInitialize(OrdersSell, false);

    for (uint i = OrdersTotal(); (bool)i--;)
      if (OrderSelect(i, SELECT_BY_POS) &&
          (OnTickMulti.IsOnlySymbolBase ||
           (// VIRTUAL::GetHandle() ? (OrderSymbolID() == Index) : // https://www.mql5.com/ru/forum/282062/page52#comment_51051261
            (OrderSymbol() == Symb))))
      {
        const ulong Magic = OrderMagicNumber();
        
        switch (OrderType())
        {
          case OP_BUY:
            OrderModify(OrderTicket(), OrderOpenPrice(), 0, Tick.bid + Magic * Offset, 0);
            OrdersBuy[Magic] = true;
            
            break;
          case OP_SELL:
            OrderModify(OrderTicket(), OrderOpenPrice(), 0, Tick.ask - Magic * Offset, 0);
            OrdersSell[Magic] = true;
            
            break;
          case OP_BUYLIMIT:
            OrderModify(OrderTicket(), Tick.ask - Magic * Offset, 0, 0, 0);
            OrdersBuy[Magic] = true;
            
            break;
          case OP_SELLLIMIT:          
            OrderModify(OrderTicket(), Tick.bid + Magic * Offset, 0, 0, 0);
            OrdersSell[Magic] = true;
            
            break;
        }
      }
    
    for (int i = 1; i <= inAmount; i++)
    {
      if (!OrdersBuy[i])
        OrderSend(Symb, OP_BUYLIMIT, 1, Tick.ask - i * Offset, 0, 0, 0, NULL, i);

      if (!OrdersSell[i])
        OrderSend(Symb, OP_SELLLIMIT, 1, Tick.bid + i * Offset, 0, 0, 0, NULL, i);
    }  
  }
}

double OnTester() { return(AccountInfoDouble(ACCOUNT_BALANCE)); }

Торговая логика советника в коде начинается с выделенной строки. Если кратко, то он просто держит несколько лимитников по обе стороны от цены. Когда лимитник срабатывает - начинает аналогично держать TP-уровень. И так по каждому заданному символу.


Результат запуска в Тестере создаст удобный HTML-отчет результатов торговли.


Виртуальное окружение.

Для запуска в виртуальном окружении нужно установить следующий входной параметр.



Сравнение сгеренированных HTML-отчетов Тестером (по тикам в режиме по пипсам) показывает идентичность результатов.


Производительность.

Время выполнения одиночного прохода в таблице (отключен Report).

MT5-Tester MT5-Tester + Virtual MT5-Tester + Virtual + SymbolID
11.421 sec. 01.720 sec.   01.157 sec.

На данном примере применение Virtual позволило получить идентичный результат в ~6.5 (~10) раз быстрее.


Технические подробности.

С вопросами и предложениями лучше в ветку обсуждения.

Ссылка на блог автора.

Поделитесь с друзьями: