可能重复:
compare floats in php
我有条件:
if($x <= .3)
echo 1;
只有当x小于.3才会回显1
如果$ x等于.3,我不会得到1。
我试过在floatval()中包装x,但没有运气
我试图回应$ x,我得到“0.3”
我试过if ($x == .3)
- 没什么
如果我尝试if (.3 == .3)
显然有效
任何想法?这是一个PHP错误吗?
答案 0 :(得分:4)
所有关于浮点数的二进制表示:
var_dump(sprintf("%.40f", 0.3));
// string(42) "0.2999999999999999888977697537484345957637"
基本上,0.3不能在基数2中精确表示,因此在几位数之后会被截断。它基本上像基数10的1/3:你可以输入0.3,但0.33更精确,因此是0.333,0.3333等。你不能完全代表它。
答案 1 :(得分:1)
浮点值不准确。您可以检查它是否大致&lt; = 0.3这样:
if ($x <= 0.3000001) {
echo 'yay';
}
答案 2 :(得分:1)
你去,大,红,胖:Floating Point Numbers:
通常是简单的小数 像0.1或0.7的分数不能 转换成内部二进制文件 对手没有一点损失 精确。这可能会导致混淆 结果:例如, 通常((0.1 + 0.7)* 10) 返回7而不是预期的8, 因为内部代表会 就像7.9。
这是因为事实确实如此 不可能表达一些分数 用有限的十进制表示法 位数。例如,1/3英寸 十进制形式变为0.3。
所以永远不要相信浮点数结果 到最后一位数, 从不比较 相等的浮点数 。 如果需要更高的精度,那么 arbitrary precision math functions和 gmp功能可用。
PS:还有更多的乐趣:
INF == INF => false
INF < INF => true
INF > INF => true
因此,无穷大不是无穷大,无穷大小于无穷大,同时大于无穷大。如果你考虑一下,它确实有一些意义......
答案 3 :(得分:0)
$x
真的不等于.3
。
我刚试过这个:
<?
$var = 0.3;
if( $var <= .3 )
{
echo 'yay';
}
else
{
echo 'boo';
}
?>
并输出yay
答案 4 :(得分:0)
$ x = .4;
if($ x&lt; = .3){echo 1; }
在这里工作正常...尝试不同的价值$ x
但是......你在哪里得到$ x ??在比较之前,您可能需要“舍入”该值。
答案 5 :(得分:0)
浮点数不是100%准确。简而言之,通常通过将1 /(2 ^ n)加在一起来存储分数分量。例如,1/2 + 1/4是如何存储3/4。所以这不是一个错误,也不是一个特定的PHP问题。
但是,这应该是真的:
$x = 0.3;
if ($x == 0.3) echo "true";
因为两者都存在相同的不准确性。
但这不能保证是真的:
$x = 0.1;
$y = 0.2;
if ($x + $y == 0.3) echo "true";
解决此问题的一种简单方法是使用delta:
if (abs($a - $b) < $delta) echo "true"
其中$ delta是一个非常小的数字。
如果您需要准确性,请查看类似BCMath扩展名的内容。
如果这是为了赚钱,那么通常更容易以整分(整数)进行计算,其中$ 1.23 = 123。