Características da linguagem mql5, subtilezas e técnicas - página 141

 

Pessoal, isto é uma coisa muito útil:

#define  abort(ANY) do{printf("abort, file=%s,  line=%i", __FILE__, __LINE__); Alert(1/(uint)MathAbs(0));}while(false)

Interrompe a execução em caso de erro crítico, nenhum destruidor será chamado (desculpe, mas pelo menos desta forma). Pelo menos alguma alternativa na ausência de análogos e excepções padrão.

Mensagem de registo:

2019.08.19 21:28:14.364 lrp_last_7 (m_GBPCHF,M1) abortar, file=lrp_last_7.mq5, line=299<br / translate="no">2019.08.19 21:28:14.364 lrp_last_7 (m_GBPCHF,M1) divisão zero em 'lrp_last_7.mq5' (299,2)
 
fxsaber:

É uma característica do testador MT5, mas decidi publicá-la neste tópico, porque está indirectamente relacionada com este assunto.

Para chegar ao separador da optimização invisível deve-se seleccionar a força bruta total sem parâmetros a optimizar.


oops, estava a pensar como obter este resultado ))

 

Os modelos em indicadores de função não funcionam em termos de sobrecarga do parâmetro de retorno?

template<typename Out>
typedef Out (*Func0)(void);

int Select(void)
{
   return 10;
}

void OnStart()
{
   Func0<int> f = Select;
}

:

'<' - unexpected token  TestObj.mq5     24      9
'>' - name expected     TestObj.mq5     24      13

Se assim for:

void OnStart()
{
   Func0 f = Select;
}

Temos isto:

'Select' - cannot resolve function address      TestObj.mq5     15      14
'Select' - type mismatch        TestObj.mq5     15      14
 
Vasiliy Sokolov:

Os modelos em indicadores de função não funcionam em termos de sobrecarga do parâmetro de retorno?

Trabalham em C++? Há um tópico especial para tais questões

 

Fórum sobre comércio, sistemas comerciais automatizados e teste de estratégias comerciais

Bibliotecas: Perito

fxsaber, 2019.09.12 06:17

Ao contrário do MT4, o MT5 não regista os parâmetros de entrada da EA quando é executado ou alterado. Por conseguinte, não há forma de distinguir do registo o que estava a correr no Terminal.

Esta função pode remediar esta situação.

#include <fxsaber\Expert.mqh> // https://www.mql5.com/ru/code/19003

// Выводит данные запущенного советника
string EAToString( const long Chart_ID = 0 )
{
  string Names[];
  MqlParam Params[];
  
  const int Flag = EXPERT::Parameters(Chart_ID, Params, Names);
  const int Size = ArraySize(Names);
  
  string Str = "Expert " + Params[0].string_value + ", expertmode = " + (string)Flag;
  
  for (int i = 0; i < Size; i++)
    Str += "\n" + Names[i] + " = " + Params[i + 1].string_value;
    
  return(Str);    
}


Candidatura

input int inInput1 = 1;
input int inInput2 = 2;

int OnInit()
{
  Print(EAToString());
  
  return(INIT_FAILED);
}


Resultado

Test8 (EURUSD,M1)       Expert Experts\Test8.ex5, expertmode = 4
Test8 (EURUSD,M1)       inInput1 = 1
Test8 (EURUSD,M1)       inInput2 = 2


SZZ Infelizmente, não funciona para guiões. O próprio MT4 mostra os parâmetros de entrada dos scripts, o MT5 não.

 
Comentários não relacionados com este tópico foram movidos para"Quaisquer perguntas de novatos sobre MQL4 e MQL5, ajuda e discussão sobre algoritmos e códigos".
 

Fórum sobre comércio, sistemas automatizados de comércio e testes de estratégia comercial

MetaTrader 5 Strategy Tester: bugs, bugs, sugestões para melhorias

fxsaber, 2019.09.18 22:32

Obtendo as últimas definições do MT5 Tester.

#include <WinAPI\fileapi.mqh>
#include <WinAPI\handleapi.mqh>

// Получает имя файла настроек последнего запуска MT5-Тестера.
string GetTesterINIFileName( ulong &Size )
{
  string Str = NULL;
  const string Path = ::TerminalInfoString(TERMINAL_PATH)+ "\\MQL5\\Profiles\\Tester\\";
  
  FIND_DATAW FindData;
  const HANDLE handle = kernel32::FindFirstFileW(Path + "*.ini", FindData);
  
  if (handle != INVALID_HANDLE)
  {     
    ulong MaxTime = 0;
    Size = 0;
    
    do
    {
      const ulong TempTime = ((ulong)FindData.ftLastWriteTime.dwHighDateTime << 32) + FindData.ftLastWriteTime.dwLowDateTime;
      
      if (TempTime > MaxTime)
      {
        MaxTime = TempTime;
        
        Str = ::ShortArrayToString(FindData.cFileName);
        Size = ((ulong)FindData.nFileSizeHigh << 32) + FindData.nFileSizeLow;;
      }      
    }
    while (kernel32::FindNextFileW(handle, FindData));    
    
    kernel32::FindClose(handle);
  }
  
  return((Str == NULL) ? NULL : Path + Str);   
}

#define  GENERIC_READ  0x80000000
#define  SHARE_READ    1
#define  OPEN_EXISTING 3

// Получает настройки последнего запуска MT5-Тестера.
string GetTesterINI( void )
{
  string Str = NULL;
  
  ulong Size;
  const string FileName = GetTesterINIFileName(Size);
  
  if (FileName != NULL)
  {
    const HANDLE handle = kernel32::CreateFileW(FileName, GENERIC_READ, SHARE_READ, 0, OPEN_EXISTING, 0, 0);
    
    if (handle != INVALID_HANDLE)
    {
      uint Read;
      ushort Buffer[];
      
      ::ArrayResize(Buffer, (int)Size / sizeof(ushort));
            
      if (kernel32::ReadFile(handle, Buffer, (int)Size, Read, 0))      
        Str = ::ShortArrayToString(Buffer);
      
      kernel32::CloseHandle(handle);        
    }
  }
  
  return(Str);
}


Candidatura

// Советник при запуске одиночного прогона возвращает свои настройки.
input int inInput1 = 1;
input int inInput2 = 2;

int OnInit()
{
  if (MQLInfoInteger(MQL_TESTER) && !MQLInfoInteger(MQL_OPTIMIZATION))
    Print(GetTesterINI());
  
  return(INIT_FAILED);
}


Resultado

2019.04.01 00:00:00   ;Одиночный тест советника: Test9, EURUSD M1, цены открытия, 2019.04.01 - 2019.09.18
2019.04.01 00:00:00   [Tester]
2019.04.01 00:00:00   Expert=Test9.ex5
2019.04.01 00:00:00   Symbol=EURUSD
2019.04.01 00:00:00   Period=M1
2019.04.01 00:00:00   Optimization=0
2019.04.01 00:00:00   Model=2
2019.04.01 00:00:00   FromDate=2019.04.01
2019.04.01 00:00:00   ToDate=2019.09.18
2019.04.01 00:00:00   ForwardMode=0
2019.04.01 00:00:00   Deposit=10000
2019.04.01 00:00:00   Currency=EUR
2019.04.01 00:00:00   ProfitInPips=1
2019.04.01 00:00:00   Leverage=100
2019.04.01 00:00:00   ExecutionMode=0
2019.04.01 00:00:00   OptimizationCriterion=6
2019.04.01 00:00:00   Visual=0
2019.04.01 00:00:00   [TesterInputs]
2019.04.01 00:00:00   inInput1=123||1||1||10||N
2019.04.01 00:00:00   inInput2=2||2||1||20||N

 

Fórum sobre comércio, sistemas comerciais automatizados e teste de estratégias comerciais

Scripts: Gráfico de Balanço HTML

fxsaber, 2019.09.19 09:56

Conversor de ficheiros de texto para MQH.

void ChangeString( string &Str )
{
  StringReplace(Str, "\\", "\\\\");
  StringReplace(Str, "\"", "\\\"");
  
  Str = "\"" + Str + "\\r\\n\" + " + "\n";
  
  return;
}

bool TextFileToMQH( const string FileNameIn, const string FileNameOut )
{
  const int handleIn = FileOpen(FileNameIn, FILE_READ | FILE_TXT | FILE_ANSI);
  bool Res = (handleIn != INVALID_HANDLE);

  if (Res)  
  {
    const int handleOut = FileOpen(FileNameOut, FILE_WRITE | FILE_TXT | FILE_ANSI);
    
    if (Res = (handleOut != INVALID_HANDLE))
    {
      FileWriteString(handleOut, "string StrMQH = \n");
      
      while (!FileIsEnding(handleIn))
      {
        string Str = FileReadString(handleIn);
  
        ChangeString(Str);
        FileWriteString(handleOut, Str);
      }

      FileWriteString(handleOut, "NULL;\n");
  
      FileClose(handleOut);            
    }
    
    FileClose(handleIn);
  }
  
  return(Res);
}

void OnStart()
{
  TextFileToMQH("Graph.txt", "Graph.mqh");
}


Permite-lhe inserir dados de texto numa fonte

#include <..\Files\Graph.mqh>
 
Características de ResourceSave
const string ResourceNameFull = ObjectGetString(0, Name, OBJPROP_BMPFILE);
ResourceSave(ResourceNameFull, "test.bmp"); // false

const string ResourceNameShort = StringSubstr(ResourceNameFull, StringFind(ResourceNameFull, "::"));
ResourceSave(ResourceNameShort, "test.bmp"); // true
 
ResourceSave não funciona no Testador. A alternativa é a seguinte.
// Сохраняет ресурс в BMP-формате.
bool ResourceSaveBMP( const string ResourceName, const string FileName )
{
  struct BMPFILEHEADER
  {
    short Type;
    uint   Size;
    short Reserved1;
    short Reserved2;
    uint   OffBits;
  };
  
  struct BMPINFOHEADER
  {    
    uint   Size;
    uint   Width;
    uint   Height;
    short Planes;
    short BitCount;
    int   Compression;
    uint   SizeImage;
    int   XPelsPerMeter;
    int   YPelsPerMeter;
    int   ClrUsed;
    int   ClrImportant;
    
    void Set( void )
    {
      this.Size = sizeof(this);
      this.Planes = 1;
      this.BitCount = 32;
      this.SizeImage = this.Width * this.Height * (this.BitCount >> 3);
      
      return;      
    }
  };
  
  struct BMPHEADER
  {
    BMPFILEHEADER File;
    BMPINFOHEADER Info;
    
    void Set( void )
    {
      this.Info.Set();

      this.File.Type = 19778;
      this.File.OffBits = sizeof(this);
      this.File.Size = this.Info.SizeImage + this.File.OffBits;
      
      return;
    }
  } BMPHeader = {0};
  
  uint Data[];  
  bool Res = ResourceReadImage(ResourceName, Data, BMPHeader.Info.Width, BMPHeader.Info.Height);
  
  if (Res)
  {
    const int handle = FileOpen(FileName, FILE_WRITE | FILE_BIN);
    
    if (Res = (handle != INVALID_HANDLE))
    {      
      BMPHeader.Set();

      uint Picture[];
      
      const uint Size = ArrayResize(Picture, ArraySize(Data));
      
      for (uint i = 0; i < Size; i += BMPHeader.Info.Width)
        ArrayCopy(Picture, Data, i, Size - i - BMPHeader.Info.Width, BMPHeader.Info.Width);
              
      FileWriteStruct(handle, BMPHeader);
      FileWriteArray(handle, Picture);
      
      FileClose(handle);
    }
  }
  
  return(Res);
}


Aplicação

  ResourceSave(ResourceName, "test.bmp");  
  ResourceSaveBMP(ResourceName, "test2.bmp");
Razão: