GNU bash, version 4.2.24:
$> printf "%.0f, %.0f\n" 48.5 49.5
48, 50
Ruby 1.8.7
> printf( "%.0f, %.0f\n", 48.5, 49.5 )
48, 50
Perl 5.12.4
$> perl -e 'printf( "%.0f, %.0f\n", 48.5, 49.5 )'
48, 50
gcc 4.5.3:
> printf( "%.0f, %.0f\n", 48.5, 49.5 );
48, 50
GHC, version 7.0.4:
> printf "%.0f, %.0f\n" 48.5 49.5
49, 50
Wikipedia says that this kind of rounding is called round half to even:
This is the default rounding mode used in IEEE 754 computing functions and operators.
Why is this rounding used by default in C, Perl, Ruby and bash, but not in Haskell?
Is it some sort of tradition or standard? And if it is a standard, why it's used by those languages and not used by Haskell? What is a point of rounding half to even?
GHCi> round 48.5
48
GHCi> round 49.5
50
The only difference is that printf
isn't using round
— presumably because it has to be able to round to more than just whole integers. I don't think IEEE 754 specifies anything about how to implement printf
-style formatting functions, just rounding, which Haskell does correctly.
It would probably be best if printf
was consistent with round
and other languages' implementations, but I don't think it's really a big deal.
"Round to even" is the default for use with IEEE 754. Haskell should probably switch to using it in printf
for consistency reasons. The relevant line of code is in
GHC.Float
f 0 (x:_) = (if x >= b2 then 1 else 0, [])
So, if someone wants to fix it, they can. As ehird points out, this would just make the roundTo
function being used by printf
consistent with round
although I'm not sure what other code this change would break.
EDIT: a previous version of this answer got the location of the rounding code wrong. The only significant difference between the two implementations is if they are hardcoded to use base 10.
I can't say for sure, but this probably has to do with the fact that this type of rounding is commonly used in accounting functions, as this is also known as Banker's rounding. If you look further at the Wikipedia article on rounding, you'll also notice this is default in IEEE 754, so likely Haskell isn't following that standard.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With