php float calculation 2 decimal point

83,766

Solution 1

Try sprintf("%.2f", $c);

Floating point numbers are represented in IEEE notation based on the powers of 2, so terminating decimal numbers may not be a terminating binary number, that's why you get the trailing digits.

As suggested by Variable Length Coder, if you know the precision you want and it doesn't change (e.g. when you're dealing with money) it might be better to just use fixed point numbers i.e. express the numbers as cents rather than dollars

$a = 3456;

$b = 3455;

$c = $b - $a;

sprintf ("%.2f", $c/100.0);

This way, you won't have any rounding errors if you do a lot of calculations before printing.

Solution 2

Use round():

$c = round($b - $a, 2);

Note: you can also choose the rounding mode as appropriate.

Edit: Ok I don't get what sprintf() is doing that number_format() isn't:

$c = number_format($b - $a, 2);

vs

$c = sprintf("%.2f", $b - $a);

?

Solution 3

You can very neatly sidestep all of these issues simply by using the bcmath library.

Just remember to read the documentation and be careful whether you are passing arguments as strings or as numeric datatypes.

Solution 4

You've run into one of the traps of floating point numbers; that they cannot always represent exact decimal fractions. If you want exact decimal values, you're better off using integers and then dividing by the precision you want at the end.

For example, if you're doing calculations in floats represeting Dollars (or your favorite currency), you may want to actually do your calculations in integer cents.

Solution 5

Native Calculation:

$a = 34.56;
$b = 34.55;
$c = $b - $a; // -0.010000000000005    

Works as expected (! use always BC functions for real number calculations, the issue is for all C based platforms):

$a = '34.56';
$b = '34.55';
$c = bcsub($b, $a, 4); // -0.0100    
Share:
83,766
Shiro
Author by

Shiro

God bless you! Thank you!

Updated on August 29, 2020

Comments

  • Shiro
    Shiro over 3 years

    Got a math calculation problem.

    $a = 34.56
    
    $b = 34.55
    

    $a do some calculation to get this figure

    $b is doing rounding to the nearest 0.05 to get this figure

    what happens is

    $c = $b - $a
    

    supposedly it be -0.01, but I echo out the $c, which shows -0.00988888888888

    I try to use number_format($c, 2), but the output is 0.00,

    how can I make sure $a and $b is exactly 2 decimals, no hidden number at the back.

    in my php knowledge, number_format is only able to format the display, but the value is not really 2 decimal,

    I hope I can get help from here. This really frustrated me.