Caratteristiche del linguaggio mql5, sottigliezze e tecniche - pagina 232

 

Spiegazione della definizione di DBL_EPSILON:

void OnStart()
  {
   double epsilon = 1.0;
   while(1.0 + epsilon != 1.0)
      epsilon /= 2;
   epsilon *= 2;

   Print(epsilon);  // 2.220446049250313e-16
  }
 
fxsaber # :

Questa è una spiegazione sbagliata, perché

Questa è una prova che le proprietà matematiche standard non sono garantite per i doppi.

L'esempio fornito utilizza la proprietà "distributiva" per la moltiplicazione.
 

Un altro modo per spiegare il significato di DBL_EPSILON:

//+------------------------------------------------------------------+
//| Returns the size of a unit in the last place (machine epsilon)   |
//| for a specified double value. This is the positive distance      |
//| between this double value and the representable value next       |
//| larger in magnitude.                                             |
//+------------------------------------------------------------------+
double machine_eps(const double value)
  {
   union _d {double value; long bits;} dbl;
   dbl.value = value;
   dbl.bits++;

   return dbl.value - value;
  }

void  OnStart()
  {
   double epsilon = machine_eps(1.0);

   Print(epsilon);   // 2.220446049250313e-16
  }

DBL_EPSILON è solo la dimensione dello spazio tra i doppi consecutivi in [1,2].

https://www.exploringbinary.com/the-spacing-of-binary-floating-point-numbers/

https://en.wikipedia.org/wiki/Machine_epsilon

 

Per comprendere meglio DBL_EPSILON, si consideri l'incremento di un contatore a virgola mobile:

//+------------------------------------------------------------------+
//| Advances a fp double value by a specified number of epsilons.    |
//+------------------------------------------------------------------+
double DoubleAdvance(const double value, const long distance)
  {
   union _d {double value; long bits;} dbl;
   dbl.value = value;
   dbl.bits += distance;

   return dbl.value;
  }

void OnStart()
  {
   double myvalue = 1.0;
   //doubel myvalue = 1024.0;

   // Print the first 10 representable numbers from the counter
   for (int i = 0; i < 10; i++)
     {
      myvalue = DoubleAdvance(myvalue, 1);  // Increment the integer representation by 1 bit
      Print(myvalue);
     }
  }

Se il valore iniziale del contatore è 1,0, la dimensione del passo (epsilon) del contatore sarà 2,220446049250313e-16 (DBL_EPSILON) ≈ 2 alla 16a posizione decimale.

/*
1.0000000000000002
1.0000000000000004
1.0000000000000007
1.0000000000000009
1.000000000000001
1.0000000000000013
1.0000000000000016
1.0000000000000018
1.000000000000002
1.0000000000000022
*/

Se il valore iniziale del contatore è 1024, la dimensione del passo (epsilon) del contatore sarà 2,27373636754432321e-13 (1024 * DBL_EPSILON) ≈ 2 al 13° decimale.

/*
1024.0000000000002
1024.0000000000005
1024.0000000000007
1024.000000000001
1024.0000000000011
1024.0000000000014
1024.0000000000016
1024.0000000000018
1024.000000000002
1024.0000000000023
*/

Se il valore iniziale del contatore è 4503599627370496 (2^52), la dimensione del passo del contatore sarà 1,0 (2^52 * DBL_EPSILON)= 1. A questo intervallo, un doppio si comporta come un contatore intero, nessuna frazione può essere rappresentata.

/*
 4503599627370497.0
 4503599627370498.0
 4503599627370499.0
 4503599627370500.0
 4503599627370501.0
 4503599627370502.0
 4503599627370503.0
 4503599627370504.0
 4503599627370505.0
 4503599627370506.0
*/

Si può notare che i numeri più piccoli hanno spazi minori tra loro, mentre i numeri più grandi hanno spazi maggiori tra loro.

Pertanto, DBL_EPSILON è il tasso di errore relativo. relativo significa relativo alla grandezza del numero.

a 1,0, l'errore assoluto = 1 * 2,2204460492503131e-016 (DBL_EPSILON).

a d, l'errore assoluto ≈ d * DBL_EPSILON.

(DBL_EPSILON è un tasso di riferimento a 1,0, come il tasso di interesse annuale della banca, ed è pari a 2^-52).


Una nota a margine: se si cerca di stampare 1024.0000000000003, verrà stampato 1024.0000000000002 (arrotondando al numero rappresentabile più vicino), perché 1024.0000000000003 non è un numero rappresentabile (numero fp inesistente).

Questo si chiama errore di rappresentazione:

void OnStart()
  {
   Print(1024.0000000000003);  // 1024.0000000000002
  }

I numeri rappresentabili precedenti/successivi vengono raggiunti attraverso la manipolazione dei bit (enum come prima: DoubleAdvance(value, -1)) o utilizzando DBL_EPSILON:

void OnStart()
  {
   double myvalue = 1024.0000000000014;
   Print( myvalue * (1 - DBL_EPSILON) );  // 1024.0000000000011
   Print( myvalue * (1 + DBL_EPSILON) );  // 1024.0000000000016
  }

DBL_EPSILON è utilizzato principalmente per stimare (o correggere) gli errori di arrotondamento di fp dopo operazioni matematiche sui doppi (analisi numerica):

|risultato vero - risultato fp| / risultato vero <= DBL_EPSILON

 

La chiamata OnTester() viene disabilitata nel tester MT5 quando è presente un algoritmo di ottimizzazione genetica e NON un criterio di ottimizzazione personalizzato?

Penso di no. Ma mi piacerebbe... Preferibilmente senza analizzare la configurazione.

PS. CARAUL!!! Tutto è andato! Ad ogni passaggio di ottimizzazione (dovrebbe/non dovrebbe) - viene chiamato OnTester(), che può aumentare di molto il tempo totale di ottimizzazione!

Aiuto a chi può... )))))

 
Potete dirmi come definire IP_ADAPTER_INFO ? La definizione del valore non è corretta
struct IP_ADAPTER_INFO {
// struct _IP_ADAPTER_INFO *Next; // Informazioni sul prossimo NIC.
uint ComboIndex; // Indice della combo & nbsp;
uchar AdapterName[256]; // Nome NIC
uchar Description[256]; // Descrizione della NIC.
uchar Address[6]; // Indirizzo MAC &nbsp uchar Address[6]; // Indirizzo MAC.
uint AddressLength; // Lunghezza indirizzo MAC
uint Indice; // indice NIC
uint Type; // Tipo di NIC Tipo NIC; // Tipo NIC
bool DhcpEnabled; // Se DHCP è abilitato o meno. nbsp;; DhcpEnabled
uchar CurrentIpAddress[16];// indirizzo IP corrente
uchar IpAddressList[16]; // Elenco di indirizzi IP.
uchar GatewayList[16]; // Gateway predefinito
uchar DhcpServer[16]; // Server DHCP
datetime LeaseObtained; // Ottenere l'ora del lease
datetime LeaseExpires; // Tempo di scadenza del lease
}; datetime LeaseObtained; // LeaseObtained.

#import "iphlpapi.dll"
int GetAdaptersInfo(IP_ADAPTER_INFO &AdapterInfo[], int &Size);
#import
 
Lo spostamento leggermente in avanti rispetto all'ora locale porta immediatamente alla disconnessione dal server commerciale.
2023.05.24 11:11:15.645 '4999464569': connection to MetaQuotes-Demo lost
 

Nella mia ricerca mi sono imbattuto in un'interessante funzione non documentata

è possibile nascondere i commenti di input per una finestra di dialogo

input int  param=0;  /* показываемый комментарий */   // комментарий для программиста

post originale qui

https://www.mql5.com/ru/forum/1271#comment_9019

Предложение по комментариям к внешним переменным
Предложение по комментариям к внешним переменным
  • 2010.06.30
  • www.mql5.com
Общее обсуждение: Предложение по комментариям к внешним переменным
 
lynxntech #:

Nella mia ricerca mi sono imbattuto in un'interessante funzione non documentata

è possibile nascondere i commenti di input per una finestra di dialogo

post originale qui

https://www.mql5.com/ru/forum/1271#comment_9019

Grazie, mi era sfuggito... Utile.
 

In Tester, la tabella Cronologia viene sovrascritta solo in due casi.

  1. Chiamata di HistorySelect.
  2. Chiamata di OnTrade (anche se non è specificato).
Questo viene fatto per risparmiare risorse. Ecco perché si può incorrere in questa ambiguità.

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

#define  Ask SymbolInfoDouble(_Symbol, SYMBOL_ASK)

void OnTick()
{
  const ulong Ticket1 = OrderSend(_Symbol, OP_BUYLIMIT, 1, Ask - 1000 * _Point, 0, 0, 0);
  const ulong Ticket2 = OrderSend(_Symbol, OP_BUYLIMIT, 1, Ask - 1000 * _Point, 0, 0, 0);

  OrderDelete(Ticket2);
  HistorySelect(0, INT_MAX); // Если убрать эту строку, то конечный Print-результат будет иным.
  
  OrderDelete(Ticket1);    
  HistorySelect(0, INT_MAX);
  
  for (int i = 0; i < HistoryOrdersTotal(); i++)
    Print(HistoryOrderGetTicket(i)); // 2 3 или 3 2.
      
  TesterStop();
}
Stringa di ricerca: Uluchshenie 064.
Motivazione: