Ermitteln der Anzahl der Dezimalstellen beliebiger Zahlen (nicht nur Anführungszeichen) unter Umgehung von Digits() in MQL4 und MQL5 - Seite 7

 

auf der Grundlage eines Artikels in den Hubs:https://habr.com/company/xakep/blog/257897/

#property copyright "IgorM"
#property link      "https://www.mql5.com/ru/users/igorm"
#property version   "1.00"
//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+
void OnStart()
  {
   double a=1.123456;
   Print(DoubleToDigits(a));
  }
//+------------------------------------------------------------------+
int DoubleToDigits(double value)
  {
   const double digits[18]={1 e17,1 e16,1 e15,1 e14,1 e13,1 e12,1 e11,1 e10,1 e9,1 e8,1 e7,1 e6,1 e5,1 e4,1 e3,1 e2,1 e1,1.0};
   double absvalue=fabs(value);
   int i,decimal=(int)absvalue;
   double real=floor((absvalue-decimal)*1 e18+0.5)-0.5;
   double normalize=fmod(real,1 e3);
   if(normalize>0.0)
     {
      if(normalize>51.5) real+=1 e3-normalize; else real-=normalize;
     }
   double res,last=0.0;
   for(i=0;i<18;i++)
     {
      res=real-fmod(real,digits[i]);
      if(last-res>=0.0) break; else last=res;
     }
   return(i);
  }
//+------------------------------------------------------------------+

nicht wirklich getestet, aber es scheint zu funktionieren

Всё, точка, приплыли! Учимся работать с числами с плавающей точкой и разрабатываем альтернативу с фиксированной точностью десятичной дроби
Всё, точка, приплыли! Учимся работать с числами с плавающей точкой и разрабатываем альтернативу с фиксированной точностью десятичной дроби
  • habr.com
Сегодня мы поговорим о вещественных числах. Точнее, о представлении их процессором при вычислении дробных величин. Каждый из нас сталкивался с выводом в строку чисел вида 3,4999990123 вместо 3,5 или, того хуже, огромной разницей после вычислений между результатом теоретическим и тем, что получилось в результате выполнения программного кода...
 
Igor Makanu:

auf der Grundlage eines Artikels in den Hubs:https://habr.com/company/xakep/blog/257897/

nicht wirklich getestet, aber es scheint zu funktionieren

Wenn das Ergebnis 0,07 lautet, funktioniert es korrekt.

 
Alexey Viktorov:

Wenn das Ergebnis 0,07 lautet, funktioniert es korrekt.

funktioniert nicht ((((

 
Igor Makanu:

funktioniert nicht ((((

Und kein Algorithmus wird funktionieren...

 
Alexey Viktorov:

Und kein Algorithmus wird funktionieren...

wird, aber das Problem ist in der gegebenen Genauigkeit und in der Zweckmäßigkeit der großen Rechenkosten, die Zahl der doppelten Präzision kann in jedem Format neu berechnet werden:±sign - (1+mantissa/252) × 2 um- 1023

Es ist einfach, die Mantisse und die Reihenfolge zu extrahieren, aber es ist nicht interessant, dieses Problem direkt zu lösen.

 
Igor Makanu:

wird, aber das Problem ist in der gegebenen Genauigkeit und in der Zweckmäßigkeit der großen Rechenkosten, die Zahl der doppelten Präzision kann in jedem Format neu berechnet werden:±sign - (1+mantissa/252) × 2 um- 1023

Es ist einfach, die Mantisse und die Reihenfolge zu isolieren, aber es ist uninteressant, dieses Problem frontal zu lösen

Wenn die Genauigkeit gegeben ist, dann macht die ganze Sache keinen Sinn. Ich habe bereits ein Beispiel genannt: 0,07 hat zwei Dezimalstellen. Wenn Sie jedoch versuchen, die Anzahl der Ziffern programmatisch zu berechnen, erhalten Sie dreizehn... Und 0,07 ist nicht das Ergebnis von Berechnungen, sondern wird manuell eingegeben, nicht einmal über eine Variable.

 

Es gibt auch diese Option:

#define  EPSILON   0.000000001
#define  MORE(A,B) ((A)-(B)>EPSILON)

int Digits(double value)
  {
   int digits=0;
   while(MORE(1.0/MathPow(10,digits),value)) 
      digits++;
   return(digits);
  }
 
Mesaoria:

Kommen Sie zur Vernunft. Das ist ein Unsinn, der nicht einmal ernsthaft diskutiert werden sollte.

Der Autor hat einfach ein völlig falsches Verständnis von der Funktionsweise von Doppelvariablen.

О!

 
Alexandr Sokolov:
Ich habe nicht behauptet, dass ich alles weiß. Sagen Sie mir lieber, was falsch ist, oder zeigen Sie mir Ihre Version.

Sie möchten wissen, wie viele Dezimalstellen jede Variable vom Typ double in Ihrem Programm definiert ist. Das ist der Unsinn. Alle Variablen vom Typ double haben die gleiche Darstellung. Sie werden als Float - Fließkomma- dargestellt. Manchmal liegt der Punkt links, manchmal rechts - das hängt vom Wert der Zahl ab. Eine Million und ein Millionstel werden mit unterschiedlicher Genauigkeit dargestellt.

 
Konstantin Gruzdev:

Es gibt auch eine solche Variante:

Nein, es wird nicht funktionieren, ich habe es gestern per Typkonvertierung gemacht, hier ist das Skript, Ihr Beispiel und meines:

#define  EPSILON   0.000000001
#define  MORE(A,B) ((A)-(B)>EPSILON)

int Digit(double value)
  {
   int digits=0;
   while(MORE(1.0/MathPow(10,digits),value)) 
      digits++;
   return(digits);
  }
//+------------------------------------------------------------------+
int DoubleToDigits(double value)
 {
   double absvalue=NormalizeDouble(fabs(value-int(value)),15);
   int res=StringLen(string(absvalue))-2;
   return(res<=0?0:res);
 }
//+------------------------------------------------------------------+
void OnStart()
  {
   double f = 122334550.007;
   Print("1. DoubleToDigits() = ",DoubleToDigits(f));
   Print("1. Digit() = ",Digit(f));
   f = 0.007;
   Print("2. DoubleToDigits() = ",DoubleToDigits(f));
   Print("2. Digit() = ",Digit(f));
  }

Ergebnisse:

2018.11.13 01:49:16.131 tst (EURUSD,M30) 1. DoubleToDigits() = 11

2018.11.13 01:49:16.131 tst (EURUSD,M30) 1. Ziffer() = 0

2018.11.13 01:49:16.131 tst (EURUSD,M30) 2. DoubleToDigits() = 3

2018.11.13 01:49:16.131 tst (EURUSD,M30) 2. Ziffer() = 3



Sie könnenFP-Printing-PLDI96. pdf googeln, aber ich bezweifle, dass jemand alles nach dem Algorithmus machen wird.