44950-7693*4.77=?
...
The result is:8254.39000000001
The correct result is:8254.39
Is there a bug in my code?
Thanks
What about parenthesis in your expression ?
44950-7693*4.77=?
...
The result is:8254.39000000001
The correct result is:8254.39
Is there a bug in my code?
I've taken to using my own two procs. to circumvent this issue.
In case it may be of interest :
Var TmpStr : String; procedure StripZero(Var S : String;NoTrail : Boolean); begin while S[length(S)] = '0' do begin S := copy(S,1,Pred(Length(S))); end; if S[length(S)] ='.' then begin if NoTrail then S := copy(S,1,Pred(Length(S))) else S := S+'0'; end; if Length(S) = 0 then S := '0'; end; procedure MakeStr(Val : single;Trail : boolean;DP : byte); begin Str(Val:4:DP,TmpStr); StripZero(TmpStr,trail); end;
If S ='' then S :=EmptyStr;
end;
Hi,Bogen85.Thanks for help.44950-7693*4.77=?
...
The result is:8254.39000000001
The correct result is:8254.39
Is there a bug in my code?
Or just use sysutils.format. It will correct the display issues for you.
https://www.freepascal.org/docs-html/rtl/sysutils/format.html
{$mode delphi} program float_precision; uses fpexprpars, sysutils; procedure primary (const parser: TFPExpressionParser); procedure do_sample (const tag, fmt, expression: string); begin parser.expression := expression; writeln (tag, ': ', expression, ' = ', format (fmt, [parser.evaluate.resFloat])); end; begin do_sample ('1', '%f', '44950-7693*4.77'); do_sample ('2', '%f', '(44950-7693)*4.77'); do_sample ('3', '%f', '44950-(7693*4.77)'); do_sample ('4', '%g', '44950-7693*4.77'); do_sample ('5', '%e', '44950-7693*4.77'); parser.free; end; function newParser: TFPExpressionParser; begin result := TFPExpressionParser.create (nil); result.builtIns := [bcMath]; end; begin primary (newParser); end.
$ fpc lazforum/60783/float_precision.pas && ./lazforum/60783/float_precision Free Pascal Compiler version 3.3.1 [2022/10/01] for x86_64 Copyright (c) 1993-2022 by Florian Klaempfl and others Target OS: Linux for x86-64 Compiling lazforum/60783/float_precision.pas Linking lazforum/60783/float_precision 36 lines compiled, 0.4 sec, 658752 bytes code, 361144 bytes data 1: 44950-7693*4.77 = 8254.39 2: (44950-7693)*4.77 = 177715.89 3: 44950-(7693*4.77) = 8254.39 4: 44950-7693*4.77 = 8254.3900000000067 5: 44950-7693*4.77 = 8.2543900000000067E+003
Results from 1 or 3 are what you are looking for.
I've taken to using my own two procs. to circumvent this issue.Thanks for sharing these codes. I will learn it.
In case it may be of interest :
Var TmpStr : String; procedure StripZero(Var S : String;NoTrail : Boolean); begin while S[length(S)] = '0' do begin S := copy(S,1,Pred(Length(S))); end; if S[length(S)] ='.' then begin if NoTrail then S := copy(S,1,Pred(Length(S))) else S := S+'0'; end; if Length(S) = 0 then S := '0'; end; procedure MakeStr(Val : single;Trail : boolean;DP : byte); begin Str(Val:4:DP,TmpStr); StripZero(TmpStr,trail); end;