note 76702 added to function.round
| From: | smithaapc at NOSPAM dot yahoo dot com | Date: | Thu, 26 Jul 2007 22:44:17 +0000 |
| Subject: | note 76702 added to function.round | ||
| Groups: | php.notes | ||
| Request: | Send a blank email to php-notes+get-128951@lists.php.net to get a copy of this message | ||
round() is broken, plain and simple. The solution must take into account all of the digits of a
given number during rounding. Truncating the number before the rounding eliminates valuable
information. Consider:
myRound(12.4444444443, 2) = 12.45 ... not quite.
Try this out instead:
function trueRound($value, $figs=1) {
if(is_numeric($value) && is_int($figs) && $figs > 0) {
// must adjust $figs down 1 for computing significant figures
$figs--;
// $prec ensures all of the original digits are included in the sprintf format
$prec = strpos($value, '.') === false ? strlen($value)-1 : strlen($value)-2;
$sci = sprintf('%.'.$prec.'e', $value);
list($sig, $mant) = explode('e', $sci);
// $base includes all of the significant digits, $test contains all the remaining digits
list($base, $test) = explode('.', $sig * pow(10, $figs));
// All 4's on the left side of $test will not be significant in the rounding
$test = preg_replace('/^4+/', '', $test);
// The first digit in $test that is not a 4 will determine the direction of the rounding
$test = preg_replace('/^(\d)\d+/', '$1', $test);
if($test > 4) {
// If the digit is > 4, then simply round up by adding 1 ...
$base += 1;
}
// ... then simply adjust the decimal point
$value = $base * pow(10, $mant-$figs);
}
return($value);
}
Note this function rounds up to a number of significant figures (all digits) rather than significant
digits (digits after the decimal point). Rounding down could be easily accomplished by passing a
switch along with the other parameters.
Mike
----
Server IP: 69.147.83.197
Probable Submitter: 129.138.12.109
----
Manual Page -- http://www.php.net/manual/en/function.round.php
Edit -- https://master.php.net/note/edit/76702
Del: integrated -- https://master.php.net/note/delete/76702/integrated
Del: useless -- https://master.php.net/note/delete/76702/useless
Del: bad code -- https://master.php.net/note/delete/76702/bad+code
Del: spam -- https://master.php.net/note/delete/76702/spam
Del: non-english -- https://master.php.net/note/delete/76702/non-english
Del: in docs -- https://master.php.net/note/delete/76702/in+docs
Del: other reasons-- https://master.php.net/note/delete/76702
Reject -- https://master.php.net/note/reject/76702
Search -- https://master.php.net/manage/user-notes.php