| Anonymous | Login | Signup for a new account | 2013-05-22 23:51 CEST | ![]() |
| All Projects | FPC | Lazarus: Packages, Patches | Lazarus CCR | Mantis | fpGUI | fpcprojects: fpprofiler |
| Main | My View | View Issues | Change Log | Roadmap |
| View Issue Details [ Jump to Notes ] | [ Issue History ] [ Print ] | ||||||||
| ID | Project | Category | View Status | Date Submitted | Last Update | ||||
| 0018704 | FPC | RTL | public | 2011-02-07 10:29 | 2012-05-19 16:55 | ||||
| Reporter | Nukool C. | ||||||||
| Assigned To | Florian | ||||||||
| Priority | normal | Severity | major | Reproducibility | always | ||||
| Status | resolved | Resolution | fixed | ||||||
| Platform | OS | OS Version | |||||||
| Product Version | Product Build | ||||||||
| Target Version | Fixed in Version | 2.7.1 | |||||||
| Summary | 0018704: CurrToStrF is not equal to FloatToStrF | ||||||||
| Description | CurrToStrF((1000000-1) / 1826, ffnumber, 4)); //547.6446 CurrToStrF((1000000-1) / 1826, ffnumber, 2)); //547.65 on FPC, 547.64 on Delphi FloatToStrF((1000000-1) / 1826, ffnumber, 10, 4)); //547.6446 FloatToStrF((1000000-1) / 1826, ffnumber, 10, 2)); //547.64 | ||||||||
| Additional Information | N/A | ||||||||
| Tags | currency | ||||||||
| FPCOldBugId | 0 | ||||||||
| Fixed in Revision | 21339 | ||||||||
| Attached Files | |||||||||
Notes |
|
|
(0045869) Zoran Vučenović (reporter) 2011-02-07 13:48 edited on: 2011-02-07 13:51 |
CurrToStrF only calls FloatToStrF and FloatToStrF also gives wrong result when called with Currency parameter! Further, FloatToStrF calls Str function, which also gives wrong result. Please see this test: program StrTest; uses sysutils; var C: Currency; D: Double; S: String; begin C := 1.45; D := 1.45; WriteLn('Using FloatToStrF:'); S := FloatToStrF(C, ffNumber, 19, 0); //we get 2 WriteLn(S, ' - Currency'); S := FloatToStrF(D, ffNumber, 19, 0); //we get 1 WriteLn(S, ' - Double'); WriteLn; WriteLn('Using Str procedure:'); Str(C:19:0, S); WriteLn(S, ' - Currency'); //we get 2 Str(D:19:0, S); WriteLn(S, ' - Double'); //we get 1 Writeln; WriteLn('Using WriteLn directly:'); WriteLn(C:19:0, ' - Currency'); //we get 2 WriteLn(D:19:0, ' - Double'); //we get 1 Readln; end. |
|
(0050638) Flávio Etrusco (mantis doesn't notify me) (reporter) 2011-08-09 13:08 |
Note: this bug is reported in the wrong project (Mantis support). |
|
(0058649) Vincent Snijders (manager) 2012-04-16 13:14 |
I just noticed this issue. I will move it to the FPC project. |
|
(0058653) Marco van de Voort (manager) 2012-04-16 18:37 |
Confirmed for 2.7.1 FreeBSD/x86_64 |
|
(0059316) Max Nazhalov (reporter) 2012-05-06 17:35 edited on: 2012-05-06 19:16 |
It seems that the problem tracks down to ".\rtl\inc\sstrings.inc::fpc_shortstr_currency()" routine. This routine always starts rounding from the least significant fractional digit towards the required one propagating the carry for every digit in the way, i.e. rounding "1.4445" to integer results in sequential steps of "1.4445"->"1.445"->"1.45"->"1.5"->"2". Precisely, this block in ".\rtl\inc\sstrings.inc::fpc_shortstr_currency()" should be completely reviewed: { rounding string if r > 0 } if r > 0 then begin ... end; Additional test is attached as CurrencyFormatTest.pp. This one also reveals several formatting glitches with leading zero. Sample output: Using Str for 1.444500000000000000E+00 frac=5, expected=1.44450, got=1.44450 frac=4, expected=1.4445, got=1.4445 frac=3, expected=1.445, got=1.445 ? frac=2, expected=1.44, got=1.45 ? frac=1, expected=1.4, got=1.5 ? frac=0, expected=1, got=2 Using Str for 1.999500000000000000E+00 frac=5, expected=1.99950, got=1.99950 frac=4, expected=1.9995, got=1.9995 frac=3, expected=2.000, got=2.000 ? frac=2, expected=2.00, got=02.00 ? frac=1, expected=2.0, got=02.0 frac=0, expected=2, got=2 Using Str for -1.999500000000000000E+00 frac=5, expected=-1.99950, got=-1.99950 frac=4, expected=-1.9995, got=-1.9995 frac=3, expected=-2.000, got=-2.000 frac=2, expected=-2.00, got=-2.00 ? frac=1, expected=-2.0, got=-02.0 frac=0, expected=-2, got=-2 Using Str for 1.994445000000000000E+02 frac=5, expected=199.44450, got=199.44450 frac=4, expected=199.4445, got=199.4445 frac=3, expected=199.445, got=199.445 ? frac=2, expected=199.44, got=199.45 ? frac=1, expected=199.4, got=199.5 ? frac=0, expected=199, got=0200 Using Str for -1.994445000000000000E+02 frac=5, expected=-199.44450, got=-199.44450 frac=4, expected=-199.4445, got=-199.4445 frac=3, expected=-199.445, got=-199.445 ? frac=2, expected=-199.44, got=-199.45 ? frac=1, expected=-199.4, got=-199.5 ? frac=0, expected=-199, got=-0200 |
|
(0059344) Max Nazhalov (reporter) 2012-05-07 10:17 |
Attached a patch that seems to resolve the problem. "currency2str_formatting.patch" fixes formatting glitches; "currency2str_rounding.patch" fixes incorrect rounding. "CurrencyFormatTest2.pp" was updated to include some more potentially weird test cases. r21245 testsuit executed with no regression. |
|
(0059350) Max Nazhalov (reporter) 2012-05-07 14:39 edited on: 2012-05-08 07:07 |
"currency2str_formatting.patch" should be replaced with "currency2str_formatting_v2.patch". Now all rounding combinations [str(c:0:0)..str(c:0:4)] formatted exactly like in Delphi. Directly tested for all numbers from -9999.9999 to 9999.9999. |
|
(0059406) Max Nazhalov (reporter) 2012-05-08 16:36 edited on: 2012-05-08 17:59 |
"CurrencyFormatTest3.pp": added a couple of numbers which are represented completely wrong with the unpatched trunk due to formatting bug. var c:currency; c:=-99.9997; writeln(c:0:3); -> "-00.000" c:=-999.9996; writeln(c:0:3); -> "-000.000" |
|
(0059427) Thaddy de Koning (reporter) 2012-05-09 13:14 |
Doesn't that break bankers rounding, which is *required* for currency? I will test this extremely well, because currency is definitly not float for rounding. And I need this not to break. |
|
(0059437) Max Nazhalov (reporter) 2012-05-09 15:05 edited on: 2012-05-09 15:39 |
Could You clarify how following numbers should be printed as "currency with 2 digits after dot"? 1.9849 1.9850 1.9851 1.9949 1.9950 1.9951 Delphi 5, Delphi 7 and Delphi XE print them as 1.98 1.99 1.99 1.99 2.00 2.00 If I understand correctly, following the "bankers' rounding" (or "round half to even") this should be 1.98 1.98 1.99 1.99 2.00 2.00 But neither Delphi, nor FPC never print like this, so there is nothing to break here. (However, it is not hard to implement such a feature) PS. FPC r21245 prints this as 1.99 1.99 1.99 02.00 02.00 02.00 |
Issue History |
|||
| Date Modified | Username | Field | Change |
| 2011-02-07 10:29 | Nukool C. | New Issue | |
| 2011-02-07 13:48 | Zoran Vučenović | Note Added: 0045869 | |
| 2011-02-07 13:51 | Zoran Vučenović | Note Edited: 0045869 | |
| 2011-08-09 13:08 | Flávio Etrusco (mantis doesn't notify me) | Note Added: 0050638 | |
| 2012-04-16 13:14 | Vincent Snijders | Note Added: 0058649 | |
| 2012-04-16 13:14 | Vincent Snijders | Project | Mantis => FPC |
| 2012-04-16 14:37 | Jonas Maebe | FPCOldBugId | => 0 |
| 2012-04-16 14:37 | Jonas Maebe | Category | => RTL |
| 2012-04-16 18:37 | Marco van de Voort | Note Added: 0058653 | |
| 2012-04-16 18:37 | Marco van de Voort | Status | new => confirmed |
| 2012-05-06 17:35 | Max Nazhalov | File Added: CurrencyFormatTest.pp | |
| 2012-05-06 17:35 | Max Nazhalov | Note Added: 0059316 | |
| 2012-05-06 19:16 | Max Nazhalov | Note Edited: 0059316 | |
| 2012-05-07 10:16 | Max Nazhalov | File Added: CurrencyFormatTest2.pp | |
| 2012-05-07 10:16 | Max Nazhalov | File Added: currency2str_formatting.patch | |
| 2012-05-07 10:17 | Max Nazhalov | File Added: currency2str_rounding.patch | |
| 2012-05-07 10:17 | Max Nazhalov | Note Added: 0059344 | |
| 2012-05-07 14:39 | Max Nazhalov | Note Added: 0059350 | |
| 2012-05-07 16:31 | Max Nazhalov | Note Edited: 0059350 | |
| 2012-05-08 07:07 | Max Nazhalov | Note Edited: 0059350 | |
| 2012-05-08 07:07 | Max Nazhalov | File Added: currency2str_formatting_v2.patch | |
| 2012-05-08 16:36 | Max Nazhalov | File Added: CurrencyFormatTest3.pp | |
| 2012-05-08 16:36 | Max Nazhalov | Note Added: 0059406 | |
| 2012-05-08 16:38 | Max Nazhalov | Note Edited: 0059406 | |
| 2012-05-08 17:59 | Max Nazhalov | Note Edited: 0059406 | |
| 2012-05-09 13:14 | Thaddy de Koning | Note Added: 0059427 | |
| 2012-05-09 15:05 | Max Nazhalov | Note Added: 0059437 | |
| 2012-05-09 15:11 | Max Nazhalov | Note Edited: 0059437 | |
| 2012-05-09 15:32 | Max Nazhalov | Note Edited: 0059437 | |
| 2012-05-09 15:39 | Max Nazhalov | Note Edited: 0059437 | |
| 2012-05-18 16:14 | Florian | Relationship added | related to 0022063 |
| 2012-05-19 16:55 | Florian | Fixed in Revision | => 21339 |
| 2012-05-19 16:55 | Florian | Status | confirmed => resolved |
| 2012-05-19 16:55 | Florian | Fixed in Version | => 2.7.1 |
| 2012-05-19 16:55 | Florian | Resolution | open => fixed |
| 2012-05-19 16:55 | Florian | Assigned To | => Florian |
| 2012-06-01 14:11 | Max Nazhalov | Tag Attached: currency | |
| Main | My View | View Issues | Change Log | Roadmap |



