PHP奇怪地减去数字 - 返回long浮点值

时间:2013-11-25 19:39:30

标签: php

我正在计算某些东西的费用(货币),当数量为0.00时,PHP表现得很奇怪。它将最终结果作为浮动数字给出,而不应该为0。

在我的数据库中,我有下表

id   |  transaction_total   |    charge_fees   |  deposit_fee   |   amount_to_customer   |   fees_minus_total_difference

因此,当我去检查以确保费用+支付的金额 - 总计= 0.00

(96.54 + .25 + 3.20 - 99.99) = 1.4210854715202E-14

为什么结果是浮点数而不是实际为零?这些数字原来是更多的小数位,但我使用number_format将它放到2个位置。例如,收费实际上可能是3.19987

number_format(3.19971,2,'.','')  //equals 3.20

当我将其保存在我的数据库中时,显示为3.20。当我在总计/费用检查的计算中使用它时,结果不是零,尽管接近。

2 个答案:

答案 0 :(得分:4)

计算机以二进制形式存储数字,因此当您尝试表示十进制数时,可能会丢失精度。这就是这里发生的事情。

有些语言具有精确的精确类型,但不幸的是,PHP没有。但它确实为您提供了BC MathGMP。但是,使用这些似乎有点矫枉过正。使用BC,你可以这样做:

bcsub(bcadd(bcadd('96.54','0.25',2),'3.20',2),'99.99',2) = 0

请注意,您还必须在此处指定小数点数(2)。

一般来说,使用浮点数和双倍用于财务是不受欢迎的,但使用PHP看起来似乎更简单。我建议您使用round()将数字四舍五入到输入的小数位数。< / p>

round(96.54 + .25 + 3.20 - 99.99,2) = 0

答案 1 :(得分:2)

除了显示字符串之外,我建议不要使用number_format()。请改用round()

你的问题是浮点数。 PHP有更准确的数学函数,你可以看看像bcadd,bcmul,bcdiv等......

http://php.net/manual/en/book.bc.php