Re: sprintf() oddness

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The 4th significant digit in both cases is '5' but in the first case, it's
rounded down but in the second case it is rounded up.  Is sprintf() basing
it's decision on the value of the 3rd significant digit?  If so, why?
Shouldn't rounding decisions be based on subsequent digits and not preceding
ones?
Actually, it's more accurate to use the preceding digit to determine rounding. What you describe is "if even then round down else round up". That's more accurate than always rounding up or always rounding down.
Please follow:
When the digit is zero, no rounding takes place.
When the digit is 1 - 4, round down.
When the digit is 6 - 9, round up.

Ok, I understand what's gong on but still not why.

Fine up to there -- but, if you always round up or down for 5, then you are introducing bias.

Fair point except...

So, if you use the even/odd value of the preceding digit to determine which way to round for 5, then it's more accurate. My rounding method doesn't always win against php's round(), but it wins more times than not. Plus, it takes a lot of rounding to introduce the bias I found and thus for most applications using the round() function (always round down) will suffice.

...consider the following example:

<script language="php">
echo '<h3>sprintf() test:<br><br>';
echo 'sprintf( "%.03f", 0.20375000 ) = ' . sprintf( '%.03f', 0.20375000 ) . '<br>'; echo 'sprintf( "%.03f", 0.17318750 ) = ' . sprintf( '%.03f', 0.17318750 ) . '<br>'; echo 'sprintf( "%.03f", 0.15485000 ) = ' . sprintf( '%.03f', 0.15485000 ) . '<br>'; echo 'sprintf( "%.03f", 0.15250000 ) = ' . sprintf( '%.03f', 0.15250000 ) . '<br>'; echo 'sprintf( "%.03f", 0.12962500 ) = ' . sprintf( '%.03f', 0.12962500 ) . '<br>'; echo 'sprintf( "%.03f", 0.11590000 ) = ' . sprintf( '%.03f', 0.11590000 ) . '<br>'; echo 'sprintf( "%.03f", 0.15750000 ) = ' . sprintf( '%.03f', 0.15750000 ) . '<br>'; echo 'sprintf( "%.03f", 0.13387500 ) = ' . sprintf( '%.03f', 0.13387500 ) . '<br>'; echo 'sprintf( "%.03f", 0.11970000 ) = ' . sprintf( '%.03f', 0.11970000 ) . '<br>'; echo 'sprintf( "%.03f", 0.15250000 ) = ' . sprintf( '%.03f', 0.15250000 ) . '<br>'; echo 'sprintf( "%.03f", 0.12962500 ) = ' . sprintf( '%.03f', 0.12962500 ) . '<br>'; echo 'sprintf( "%.03f", 0.11590000 ) = ' . sprintf( '%.03f', 0.11590000 ) . '<br>'; echo 'sprintf( "%.03f", 0.07875000 ) = ' . sprintf( '%.03f', 0.07875000 ) . '<br>'; echo 'sprintf( "%.03f", 0.06693750 ) = ' . sprintf( '%.03f', 0.06693750 ) . '<br>'; echo 'sprintf( "%.03f", 0.05985000 ) = ' . sprintf( '%.03f', 0.05985000 ) . '<br>'; echo 'sprintf( "%.03f", 0.13125000 ) = ' . sprintf( '%.03f', 0.13125000 ) . '<br>'; echo 'sprintf( "%.03f", 0.13375000 ) = ' . sprintf( '%.03f', 0.13375000 ) . '<br><br>';
echo '<h3>round() test:<br><br>';
echo 'round( 0.20375000, 3 ) = ' . round( 0.20375000, 3 ) . '<br>';
echo 'round( 0.17318750, 3 ) = ' . round( 0.17318750, 3 ) . '<br>';
echo 'round( 0.15485000, 3 ) = ' . round( 0.15485000, 3 ) . '<br>';
echo 'round( 0.15250000, 3 ) = ' . round( 0.15250000, 3 ) . '<br>';
echo 'round( 0.12962500, 3 ) = ' . round( 0.12962500, 3 ) . '<br>';
echo 'round( 0.11590000, 3 ) = ' . round( 0.11590000, 3 ) . '<br>';
echo 'round( 0.15750000, 3 ) = ' . round( 0.15750000, 3 ) . '<br>';
echo 'round( 0.13387500, 3 ) = ' . round( 0.13387500, 3 ) . '<br>';
echo 'round( 0.11970000, 3 ) = ' . round( 0.11970000, 3 ) . '<br>';
echo 'round( 0.15250000, 3 ) = ' . round( 0.15250000, 3 ) . '<br>';
echo 'round( 0.12962500, 3 ) = ' . round( 0.12962500, 3 ) . '<br>';
echo 'round( 0.11590000, 3 ) = ' . round( 0.11590000, 3 ) . '<br>';
echo 'round( 0.07875000, 3 ) = ' . round( 0.07875000, 3 ) . '<br>';
echo 'round( 0.06693750, 3 ) = ' . round( 0.06693750, 3 ) . '<br>';
echo 'round( 0.05985000, 3 ) = ' . round( 0.05985000, 3 ) . '<br>';
echo 'round( 0.13125000, 3 ) = ' . round( 0.13125000, 3 ) . '<br>';
echo 'round( 0.13375000, 3 ) = ' . round( 0.13375000, 3 ) . '<br><br>';
</script>

Why is the behavior of round() different to that of sprintf()? Both are rounding numbers. I'll grant you that sprintf() has more utility and does more things than round() but when you are dealing with numbers (and more specifically, when you've used a numeric type specifier in the format argument), sprintf() is doing the same type of thing to the value -- rounding. So why are they doing it differently? Is that a bug? I'm reticent to say that but it doesn't make sense to me that they would behave differently. If the general rule is to round up for 5s when preceeding is odd and round down when even, that's not occuring here when using round().

thnx,
Christoph
--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php


[Index of Archives]     [PHP Home]     [Apache Users]     [PHP on Windows]     [Kernel Newbies]     [PHP Install]     [PHP Classes]     [Pear]     [Postgresql]     [Postgresql PHP]     [PHP on Windows]     [PHP Database Programming]     [PHP SOAP]

  Powered by Linux