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

 
Alexey Viktorov:

Só não se deve esperar que, se não houver valor, seja necessariamente 0 e correspondentemente falso se não for uma variável do tipo bool. Mesmo uma conversão explícita em bool não vai ajudar.

Funciona desta forma sem erros.

Sinceramente, não compreendo de onde vem o zero:

const double Points = TickValue[0] ? Profit / (Lots * TickValue[0] * _Point) : 0; // zero divide

TickValue[0] contém lixo. Pode ou não ser igual a zero.

Se o lixo em TickValue[0] não for igual a zero, então calculamos Pontos = Lucro / Lotes * lixo não zero * _Ponto, caso contrário, se o lixo em TickValue[0] for igual a zero - igualamos Pontos a zero.

E onde é que a expressão Lotes * lixo não zero * _Ponto recebe zero, se Lotes é inicializado com um quando declarado? Házero em _Point?

 
fxsaber:

O erro é, de facto, claro.

OK, o erro não é claro. E também não se está a reproduzir para mim.

 
TheXpert:

Ok, o erro é incompreensível. E não se reproduz em mim.

Grosseiramente falando, chamar a esta função pode causar divisão por zero.

// Неправильно написанная функция.
double WrongFunc( const double Num )
{
  return(Num ? 1 / (0.1 * Num) : 0);
}


Encontrei este problema na prática na biblioteca do Relatório. Depois percebi que é lógico.

 
fxsaber:

Grosseiramente falando, chamar a esta função pode causar divisão por zero.

Tenho este código nos rublos de fronteira, mas ele não se estraga

double f( const double Num )
{
  return(Num ? 1 / (0.1 * Num) : 0);
}

void OnStart()
{
  Print(f(1 e-308));  // 2019.10.28 13:02:19.457	test (USDJPY,H1) inf
}
 
TheXpert:

Recebo o mesmo código nos rublos de fronteira, mas não cai

#include <TypeToBytes.mqh> // https://www.mql5.com/ru/code/16280

void OnStart()
{
  double Num = 0;
  
  _W(Num) = (uchar)2;
  
  Print(WrongFunc(Num));
}
 
fxsaber:
uma tal encolhimento.
 
TheXpert:
um tal acidente.

Em resumo, a multiplicação de dois doublets não zero pode dar zero. E este não é um caso degenerado, mas um caso real na prática.

Grosso modo, uma EA de combate pode quebrar devido a isto com uma probabilidade longe de zero.

 
E a verificação de zero não salvará, nem explícita nem implicitamente (conversão bool)
 
TheXpert:
E a verificação de zero não salvará, nem explícita nem implicitamente (conversão bool)
  return(0.1 * Num ? 1 / (0.1 * Num) : 0);
 
fxsaber:

Em resumo, a multiplicação de dois doublets não zero pode dar zero. E este não é um caso degenerado, mas um caso real na prática.

Grosso modo, uma EA de combate pode quebrar devido a isto com uma probabilidade longe de zero.

na NaN, é necessário verificar adicionalmente, muito provavelmente este código funcionaráhttp://qaru.site/questions/20557/checking-if-a-double-or-float-is-nan-in-c

f != f

ou limitar a precisão, como em CompareDoubles() exemplo - parece estar em SBhttps://www.mql5.com/ru/docs/basis/types/double