View Issue Details

IDProjectCategoryView StatusLast Update
0036867FPCOtherpublic2020-04-13 13:55
ReporterChristophe Assigned ToFlorian  
PrioritynormalSeverityminorReproducibilityalways
Status resolvedResolutionfixed 
PlatformPC x64OSWindows 
Product Version2.0.2 
Summary0036867: trystrtofloat donne une valeur incorrecte
DescriptionMettant au point une fonction d'arrondi complexe, je n'arrivai pas à la mettre au point.
En exécution pas à pas, je me suis aperçu qu'une chaîne n'était pas toujours correctement transformée en double :
En effet : 1.1 devient 1.10000000000000001
(voir copie d'écran ci-joint)

Ce problème est la raison qui fait que ma fonction d'arrondi à 2 décimales arrondi 1.1 à 1.11 au lieu de 1.10
Steps To ReproduceExécution pas à pas de
procedure TForm1.Button1Click(Sender: TObject);
var x1,double;
begin
   Edit1.text:='1.1';
   if not trystrtofloat(edit1.text,x1) then exit;
end;

Et afficher la valeur de x1 (ou de x2) en mode déboggage (comme la copie d'écran)

Additional InformationJ'espère avoir poster au bon endroit. Si ce n'est pas le cas, merci de m'en excuser.
TagsNo tags attached.
Fixed in Revision
FPCOldBugId
FPCTarget-
Attached Files

Relationships

duplicate of 0029531 new string to double conversion rounded wrong 

Activities

Christophe

2020-04-03 22:36

reporter  

bug.png (13,929 bytes)   
bug.png (13,929 bytes)   

Bart Broersma

2020-04-03 23:36

reporter   ~0121874

Last edited: 2020-04-03 23:37

View 2 revisions

English please.
1.1 cannot be exactly represented as a floating point value, so this is normal.
Please ask first on the forum or ML before posting bugreports.
Also this is about the compiler, not about Lazarus, so you posted this in the wrong section.

Moving to FPC.

Anton Kavalenka

2020-04-04 09:13

reporter   ~0121884

Last edited: 2020-04-04 09:13

View 2 revisions

By design IEEE-754 64-bit floats (https://en.wikipedia.org/wiki/IEEE_754) have 15 significant decimal digits.
Excessive digits should be dropped.

Max Nazhalov

2020-04-04 10:10

reporter   ~0121887

@Anton
Please, read the "Character representation" section of the article You've linked to. It clearly states "17 decimal digits for binary64" may be required to preserve internal identity during back and forth conversions.

Florian

2020-04-05 18:29

administrator   ~0121949

@Max: afaik you contributed the/to? the conversion routines. What's your opinion on the report?

Max Nazhalov

2020-04-05 19:09

reporter   ~0121950

Last edited: 2020-04-05 23:29

View 3 revisions

The main problem is INPUT routine (str->float). There is no precise solution for it yet without involving bignums, AFAIK. Current implementation in RTL uses strightforward fixed-precision arithmetic approach, despite of the excess precision, it is still imperfect in many cases. However it is still within IEEE standard requirements, which are relaxed in this field due to the problem complexity. Given 17-digit input it will provide original binary64.
Regarding OUTPUT problem -- current implementation uses Grisu1 variant, which is fast, fixed-precision, and accurate, but sometimes produces some irremovable noise in the least-significant digits. The better variant -- Grisu2 -- is also accurate, fixed-precision, and somewhat even faster then Grisu1, produces much finer output, BUT breaks current imperfect input routine -- some pecular numbers printed with Grisu2 (refined to less then 17 digits) cannot be read back correctly with current str->float approach, despite of the representation is correct and minimal, and can be read by arbitrary-precision implementation. And this variant still gives some noisy output, but MUCH less frequently. The last variant, Grisu3, is equal to variant 2, but it just gives-up if it cannot guarantee the minimal representation, so there must be arbitrary-precision fallback accompanying.
I've tested Grisu2 -- there is indeed not much work to turn current implementation into it, but without completely new INPUT approach it is worth nothing, IMHO.
So I'm personally suspended for now..

Regarding this particular report -- as already Bart said, this behavior is normal for current implementation.

edit: BTW, most of this already had been discussed years ago within 0029531; plugin approach was declined.

Issue History

Date Modified Username Field Change
2020-04-03 22:36 Christophe New Issue
2020-04-03 22:36 Christophe File Added: bug.png
2020-04-03 23:36 Bart Broersma Note Added: 0121874
2020-04-03 23:37 Bart Broersma Note Edited: 0121874 View Revisions
2020-04-03 23:37 Bart Broersma Project Lazarus => FPC
2020-04-04 09:13 Anton Kavalenka Note Added: 0121884
2020-04-04 09:13 Anton Kavalenka Note Edited: 0121884 View Revisions
2020-04-04 10:10 Max Nazhalov Note Added: 0121887
2020-04-05 18:29 Florian Note Added: 0121949
2020-04-05 19:09 Max Nazhalov Note Added: 0121950
2020-04-05 19:17 Max Nazhalov Note Edited: 0121950 View Revisions
2020-04-05 23:29 Max Nazhalov Note Edited: 0121950 View Revisions
2020-04-13 13:55 Florian Assigned To => Florian
2020-04-13 13:55 Florian Status new => resolved
2020-04-13 13:55 Florian Resolution open => fixed
2020-04-13 13:55 Florian FPCTarget => -
2020-04-13 13:55 Florian Relationship added duplicate of 0029531