Erros, bugs, perguntas - página 2657

 
Stanislav Korotky:

É isso mesmo, a árvore de classe tem um nó comum CWnd (CObject está mais longe, na raiz).

CButton -> CWndObj -> CWnd -> CObject.

Se alterar o parâmetro no método para CObject, obtém 2 vezes mais erros:

Uma hierarquia de classes semelhante funciona para o caso não-radicalado. Aqui está o código compilado:

A questão é como fazer com que funcione também para uma matriz?

Sei que um modelo ajuda, mas só quero evitá-lo.

IMHO, deve funcionar sem modelos por direito sucessório.

Verifiquei-o como em C++.

Funciona. Mas a MQL não a digere - tanto com como sem o índice.

Para C++, o seu exemplo será muito mais claro. Basta executá-lo e ver como funciona))))

class CWnd
{
public:
    int x;
    CWnd(int _x = 10) : x(_x) {}
};
class CButton : public CWnd
{
    int a;
public:
    CButton(int _a=6) : CWnd(),a(_a) {}
};

class Collection
{
public:
    Collection(CWnd* ptr,size_t size) {
        for (int i = 0; i < size; cout << ptr[i++].x<<endl);
    }
};

int main()
{
    CButton buttons[10];
    CWnd wnd[10];
    Collection data1(&wnd[0],_countof(wnd));
    cout << "------------------------------" << endl;
    Collection data2(&buttons[0],_countof(buttons));
    return 0;
}
 

Sim, erro meu. Mas depois surge a seguinte questão. Este código C++ funciona (já exactamente à direita ;-))).

class Base
{
  public:
    virtual void method1(void) { cout << "2\n"; }
};

class Derived: public Base
{
  public:
    virtual void method1(void) override { cout << "3\n"; }
};

template<typename T>
class Wrapper
{
  public:
    Wrapper(T *ptr)
    {
      ptr->T::method1();
    }
};

int main()
{
  Derived d;
  d.Base::method1();   // ok
  Wrapper<Base> w(&d); // ok

  return 0;
}

MQL semelhante dá erro:

class Base
{
  public:
    virtual void method1(void) { Print(__FUNCSIG__); }
};

class Derived: public Base
{
  public:
    virtual void method1(void) override { Print(__FUNCSIG__); }
};

template<typename T>
class Wrapper
{
  public:
    Wrapper(T *ptr)
    {
      ptr.T::method1(); // <<< 'Base' is not a class, struct or union
    }
};


void OnStart()
{
  Derived d;
  d.Base::method1();   // ok
  Wrapper<Base> w(&d); // causes the error above
 
Stanislav Korotky:

Sim, erro meu. Mas depois surge a seguinte questão. Este código C++ funciona (já exactamente à direita ;-))).

Um MQL semelhante dá um erro:

Não conheço a tarefa, mas penso que está à procura de algo como isto:

typedef void(*PTR)(void);

em MQL isto é um ponteiro para uma função func(void)

numa classe, pode declarar um campo do tipo PTR e depois atribuir-lhe uma função, e depois "desreferenciar o ponteiro" e chamar a função

a passagem de funções escritas em estilo processual na classe funciona sem qualquer problema, os métodos de classe provavelmente não podem ser passados tão facilmente, pode tentar usar o dynamic_cast, mas o código vai ficar muito confuso

 
Igor Makanu:

Não conheço a tarefa, mas penso que está à procura de algo como isto:

em MQL é um ponteiro para uma função func(void)

numa classe, pode declarar um campo do tipo PTR e depois atribuir-lhe uma função e depois "desreferenciar o ponteiro" e chamar a função

a passagem de funções escritas em estilo processual na classe funciona sem qualquer problema, os métodos de classe provavelmente não podem ser passados tão facilmente, pode tentar usar o dynamic_cast, mas o código vai ficar muito confuso

O dactilografado não funcionará com um método.

dynamic_cast trabalha para o herdeiro (cadeia mais longa), ou seja, se o ponteiro para base contém derivado, então pode lançar para derivado e se não for NULL (isto é, lançar normal), chamar o seu método. Mas quando a situação é oposta, como no meu caso, há um ponteiro para derivar então, por definição, é também base. E qualquer invocação do seu método virtual descobre que derivada é "sentada" no ponteiro e chamadas anuladas de implementação. A base é necessária.

Existe a construção sintáctica acima mencionada em C++ para este fim, mas MQL não é C++. Aparentemente, ainda não há maneira de o fazer.

Fiz um trabalho de volta, mas pode não funcionar bem em todas as tarefas.

O objectivo de toda esta dança de tamborim, como sempre, é manter o código emaranhado dentro da "biblioteca" e tornar o código que o utiliza cristalino e simples.

 

o que rubricar rand() no testador com ?

código:

input ulong param = 18446744073709551615;
void OnTick()
   {
   }
//+------------------------------------------------------------------+
double OnTester()
   {
      srand(GetTickCount()); 
      return(rand());
   }
//+------------------------------------------------------------------+

Eu não gosto muito deste tipo de geração pseudo-aleatória:


 
Igor Makanu:

o que rubricar rand() no testador com ?

código:

Não gosto muito deste tipo de geração pseudorandômica:


Ajuda:MathRand

Nota

Antes de chamar a função pela primeira vez, é necessário utilizaro MathSrand para definir o gerador de números pseudo-aleatórios para o estado inicial.


Experimente-o agora com MathSrand.

Документация по MQL5: Математические функции / MathRand
Документация по MQL5: Математические функции / MathRand
  • www.mql5.com
Математические функции / MathRand - справочник по языку алгоритмического/автоматического трейдинга для MetaTrader 5
 
Vladimir Karputov:

Ajuda:MathRand

Nota

A funçãoMathSrand deve ser utilizada antes da primeira chamada de função para definir o gerador de números pseudorandômicos para o estado inicial.

Obrigado Cap !

Estamos a falar do testador.

este código também não funciona no testador

input ulong param = 18446744073709551615;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
   {
   MathSrand(GetTickCount()); 
   return(INIT_SUCCEEDED);
   }
//+------------------------------------------------------------------+
void OnTick()
   {
   }
//+------------------------------------------------------------------+
double OnTester()
   {
      return(rand());
   }
//+------------------------------------------------------------------+
 
Igor Makanu:

Penso que, se um testador, não há necessidade de usar MathSrand.

Mas se isso não ajudar, muito provavelmente o testador está a forçar a MathSrand(GetTickCount()) em algum momento.

Depois tente MathSrand(int(GetMicrosecondCount()%1000000)));

Lembre-se, GetTickCount() muda o seu valor de 15,625 milissegundos em cada 15,625 milissegundos. É um intervalo de tempo muito longo para um testador.

 
Nikolai Semko:

Penso que, se um testador, não há necessidade de usar MathSrand.

isto contradiz a documentaçãohttps://www.mql5.com/ru/docs/math/mathrand

Antes da primeira chamada de função, é necessário utilizar a função MathSrand para definir o gerador de números pseudo-aleatórios para o estado inicial.

Não quero passar pelo código fonte, mas para pacotes de redes neurais a inicialização por valor aleatório de pesos NS é obrigatória, suspeito que isto foi feito de acordo com o material de ajuda MQL - ou seja, foi utilizado srand()

ou seja, o uso de programas MQL dentro do testador com tais pacotes de NS terá muito provavelmente lugar num único núcleo processador - os pesos iniciais de NS terão os mesmos valores, certo?

é ainda mais fresco sem srand()

int OnInit()
   {
   return(INIT_SUCCEEDED);
   }
//+------------------------------------------------------------------+
void OnTick()
   {
   }
//+------------------------------------------------------------------+
double OnTester()
   {
      return(rand());
   }
//+------------------------------------------------------------------+
 
Igor Makanu:

isto contradiz a documentaçãohttps://www.mql5.com/ru/docs/math/mathrand

Não quero olhar através do código fonte, mas para pacotes de redes neurais a inicialização por valor aleatório de pesos NS é obrigatória, suspeito que isto foi feito de acordo com o material de ajuda MQL - ou seja, foi utilizado srand()

ou seja, o uso de programas MQL dentro do testador com tais pacotes de NS terá muito provavelmente lugar num único núcleo processador - os pesos iniciais de NS terão os mesmos valores, certo?

ainda mais engraçado sem srand()

Igor, bem então experimente MathSrand(int(GetMicrosecondCount()%16384)));

Como será que a imagem irá mudar?