Minha abordagem. O núcleo é o motor. - página 124

 
Andrey Barinov:

Porque ao invés de OrderOpenPrice colocar OrderOpenTime()

Certo. Eu me confundi. :)

 
Реter Konow:

Tenho que admitir que fiquei um pouco surpreso com os resultados dos testes.

É por isso que eu queria que você fizesse tudo sozinho, não para dar soluções prontas que batessem na parede.
Você sabe, Peter, existe também um recurso como um ponteiro para uma função, graças ao qual você pode organizar chamadas de função simplesmente tomando estas indicações de um conjunto de tais indicações. Acho que isto seria muito útil em sua tarefa. O único problema é que você tem que mexer com as aulas novamente.
 
Nikolai Semko:
É por isso que eu queria que você fizesse tudo sozinho, não para dar soluções prontas, que são como ervilhas contra a parede.
E você sabe, Peter, também existe uma coisa como um ponteiro para uma função, graças à qual você pode organizar chamadas de função simplesmente tomando estas indicações de uma série de tais indicações. Acho que isto seria muito útil em seu problema. Mas aqui está o problema - você tem que lidar com as aulas novamente.

Ouvi falar de indicadores de funções. Mas eu tenho muito poucas funções. É por causa disso que eu não tenho espaço e preciso usar o OOP.

Eu tenho um conceito de desenvolvimento diferente. Acredito que a operação de blocos holísticos multifuncionais é mais eficiente do que a de grandes complexos de pequenas funções.

Mais promissor, do ponto de vista do desenvolvimento do mecanismo.

Essa é a minha opinião...

Eu tenho vários blocos grandes. Para aplicar o OOP, eles devem ser divididos em pequenas funções, organizados em classes e, em seguida, usar apontadores e outras coisas.

Mas não serei capaz de fazer isso. Simplesmente porque eu penso de maneira diferente.

O conceito de OOP não coincide com as peculiaridades do meu modo de pensar, e não posso expandi-lo nele. Essa é a razão.

 
Nikolai Semko:

Note, Nikolai, que em matéria de desenvolvimento programático, eu não tenho nenhum problema. Tudo está se desenvolvendo muito rapidamente.

Ao mesmo tempo, os mecanismos funcionam bem.

Agora domino os sindicatos, e vejo sua aplicação em uma tarefa específica, - escrever cordas em um recurso.

Vou tentar verificar a velocidade e a carga da CPU no teste EA e postar o resultado.

Se for bom, reconstruirei a comunicação entre o motor e a EA, fazendo-a sobre os recursos.

 

Para utilizar recursos para passar cordas de comprimento indefinido, essas cordas devem ser escritas em uma matriz de caracteres.

No entanto, parece que seu tamanho só é declarado dentro do sindicato e não muda depois.

Tentei redimensionar o char array do sindicato, através do ArrayResize, mas não há nenhum efeito.

Parece que o tamanho da matriz de caracteres deve ser definido de antemão. E deve ter o tamanho máximo.


Aqui está o código:

//+------------------------------------------------------------------+
//|                                                       TEST_2.mq4 |
//|                                                      Peter Konow |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Peter Konow"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict
//+------------------------------------------------------------------+
union Char_Uint
  {
   uchar   Char[4];
   uint    Uint[1];   
  };
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
   EventSetMillisecondTimer(1000);
   //----------------------------------------------
   if(!ObjectCreate(0,"Resource",OBJ_BITMAP_LABEL,0,0,0))Print("Object is not created!  ",GetLastError());
   else Print("Object created!");
   //-------------------------------
   if(!ObjectSetString(0,"Resource",OBJPROP_BMPFILE,"::Resource"))Print("BMPFILE is not created!");
   else Print("BMPFILE created!");
   //----------------------------------------------
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//--- destroy timer
   EventKillTimer();
   
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
//---
   
  }
//+------------------------------------------------------------------+
//| Timer function                                                   |
//+------------------------------------------------------------------+
void OnTimer()
  {
   Char_Uint u;
   string String = NULL;
   int q = MathRand();
   if(q > 10000)q = 10000;
   //-------------------------------------------------------
   //Формируем случайную строку.
   //-------------------------------------------------------
   for(int a1 = 0; a1 < q; a1++)String += (string)a1 + "^";
   //-------------------------------------------------------
   //Получаем размер собранной строки.
   //-------------------------------------------------------
   int StrSize = StringLen(String);
   //-------------------------------------------------------
   //Меняем размер массива из Char[] юниона. 
   //-------------------------------------------------------
   ArrayResize(u.Char,StrSize);
   //-------------------------------------------------------
   //Копируем строку в массив Char[].
   //-------------------------------------------------------
   //StringToCharArray(String,u.Char);
   //-------------------------------------------------------
   //
   //-------------------------------------------------------
   Print("StrSize  ",StrSize," Размер u.Char  ",ArraySize(u.Char));
  }
//+------------------------------------------------------------------+
 

Agora está claro que o tamanho da matriz decarvão no sindicato deve ser conhecido de antemão. Porque oArrayResize(u.Char,StrSize) não o altera.

Portanto, temos de definir o tamanho da matriz igual ao comprimento máximo da corda.

 

Boas notícias. Tudo está funcionando bem.

O fio é escrito ao recurso e lido por outro EA em um gráfico diferente.

Não há carga sobre o processador. A carga é causada apenas pela chamada do Alerta que imprime a corda.

Aqui está o código de Conselheiros Especialistas:

1. Conselheiro especializado formando o cordel e escrevendo-o em um recurso.

//+------------------------------------------------------------------+
//|                                                       TEST_2.mq4 |
//|                                                      Peter Konow |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Peter Konow"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict
//+------------------------------------------------------------------+
union Char_Uint
  {
   uchar   Char[32000];
   uint    Uint[8000];   
  };
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
   EventSetMillisecondTimer(16);
   //----------------------------------------------
   if(!ObjectCreate(0,"Resource",OBJ_BITMAP_LABEL,0,0,0))Print("Object is not created!  ",GetLastError());
   else Print("Object created!");
   //-------------------------------
   if(!ObjectSetString(0,"Resource",OBJPROP_BMPFILE,"::Resource"))Print("BMPFILE is not created!");
   else Print("BMPFILE created!");
   //----------------------------------------------
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//--- destroy timer
   EventKillTimer();
   
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
//---
   
  }
//+------------------------------------------------------------------+
//| Timer function                                                   |
//+------------------------------------------------------------------+
void OnTimer()
  {
   Char_Uint u;
   string String = NULL;
   int q = MathRand(),width,height;
   if(q > 1000)q = 1000;
   //-------------------------------------------------------
   //Формируем случайную строку.
   //-------------------------------------------------------
   for(int a1 = 0; a1 < q; a1++)String += (string)a1 + "^";
   //-------------------------------------------------------
   //Получаем размер собранной строки.
   //-------------------------------------------------------
   int StrSize = StringLen(String);
   //-------------------------------------------------------
   //Копируем строку в массив Char[].
   //-------------------------------------------------------
   StringToCharArray(String,u.Char);
   //-------------------------------------------------------
   //Cохраняем строку переведенную в байты в ресурсе.
   //-------------------------------------------------------
   if(!ResourceCreate("::Resource",u.Uint,8000,1,0,0,0,COLOR_FORMAT_XRGB_NOALPHA))Print("Resource is not created!");
   //-------------------------------------------------------
  }
//+------------------------------------------------------------------+
 

Um conselheiro lendo uma linha de um recurso em outro gráfico:

//+------------------------------------------------------------------+
//|                                              Resource reader.mq4 |
//|                                                      Peter Konow |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Peter Konow"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict

//+------------------------------------------------------------------+
union Char_Uint
  {
   uchar   Char[32000];
   uint    Uint[8000];   
  };
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- indicator buffers mapping
   EventSetMillisecondTimer(16); 
   
   if(!ObjectSetString(0,"Resource",OBJPROP_BMPFILE,"\\Experts\\TEST_2.ex4::Resource"))Print("Resource is not connected!");
   else Print("Resource connected!");
//---
   return(INIT_SUCCEEDED);
  }


//+------------------------------------------------------------------+
//| Timer function                                                   |
//+------------------------------------------------------------------+
void OnTimer()
  {
//---
   Char_Uint u;   
   uint width,height;
   //string Message; 
   //-----------------------------
   if(!ResourceReadImage("\\Experts\\TEST_2.ex4::Resource",u.Uint,width,height))Print("Failed to read resource!  ",GetLastError());
   //-----------------------------
   string String = CharArrayToString(u.Char);
   //-----------------------------
   Alert("  String  ",String);
   //-----------------------------
  }
//+------------------------------------------------------------------+


Utilizará recursos para a comunicação. A única desvantagem é que você tem que definir o tamanho máximo da matriz de carvão no sindicato. Mas, não é preciso pensar no tamanho da corda e no número de objetos de MT.

Este método é mais lento do que o método de ligação MT-objeto, mas está bem.

 
Реter Konow:

Você tem uma teoria interessante, embora não corresponda bem aos resultados de meus experimentos, que agora vou postar abaixo.

Como o teste mostra, é a inicialização da matriz de pixels que mais carrega a CPU.

Confira o teste EA abaixo.

Reler a tarefa:

Vasiliy Sokolov:

Peter, aqui está a tarefa. Faça um painel mostrando as aberturas de pedidos atuais no MT4. Você não precisa fazer uma cópia completa do painel do sistema, apenas fazer uma simples tabela com propriedades básicas de pedidos abertos: preço aberto, direção, lucro. O resto é com você. O principal é que quando uma ordem é fechada, sua indicação em sua mesa também desapareceria. E vice versa, apareceria nesta tabela quando uma nova ordem fosse aberta.

Aqui você pode ver as duas operações necessárias de redesenhar quando a tabela muda na tela: 1. ao fechar um comércio e 2. ao abrir um comércio. Por que redesenhar os pixels no resto do tempo?

Você está resolvendo algum outro problema?

 
Vladimir:

Reler o problema:

Vasiliy Sokolov:

Aqui vemos duas operações de redesenho necessárias quando a tabela muda na tela: 1. ao fechar um comércio e 2. ao abrir um comércio. Por que redesenhar pixels em outros momentos?

Você está resolvendo algum outro problema?

Bem, eles são redesenhados exatamente como você disse.

A carga sobre o processador aparece durante a animação:

Há uma reinicialização constante dos valores na matriz de píxeis. A cada 16 milissegundos. Isto carrega o processador em até 40%.

Eu estava tentando descobrir o que é exatamente a carga. Pensei que estava economizando um recurso ou lendo-o. Acontece que foi a reinicialização da matriz no circuito de desenho.


Também se verificou que uma chamada constante de ObjectSetInteger(0, "objeto MT",OBJPROP_SELECTED,1); (a cada 16 ms) também carrega o processador. Em cerca de 10%.

Uso esta chamada para dizer a outro EA para ler o recurso com dados de animação.

No total, ele recebe +~50% de carga de CPU durante a animação.

Razão: