首页 > 解决方案 > PHP浮点循环不匹配值

问题描述

我有一个我无法弄清楚的最奇怪的错误。

我正在遍历值并检查它们是否等于浮点数。

奇怪的是,它适用于某些价值观,但不适用于让我的大脑融化的其他价值观。当我进行直接比较时它“匹配”但是当在循环中创建 $num1 时它不再喜欢它了

例如 0.1, 0.2 都返回匹配,但 0.3 不返回!?

$num1 = 0.3;
$num2 = 0.3;

var_dump($num1);
var_dump($num2);

if ($num1 == $num2) {
    echo "*** MATCH ***<br>";
} else {
    echo "NO MATCH<br>";
}

echo "<hr>";

for ($num1=0; $num1 < 0.6; $num1 = $num1 + 0.1) {
var_dump($num1);
var_dump($num2);


if ($num1 == $num2) {
    echo "*** MATCH ***<br>";
} else {
    echo "NO MATCH<br>";
}

echo "<hr>";
}

上面的代码返回

float(0.3) float(0.3) *** MATCH ***
int(0) float(0.3) NO MATCH
float(0.1) float(0.3) NO MATCH
float(0.2) float(0.3) NO MATCH
float(0.3) float(0.3) NO MATCH
float(0.4) float(0.3) NO MATCH
float(0.5) float(0.3) NO MATCH

例如,如果我将 $nums 更改为 0.2,那么它可以工作!

float(0.2) float(0.2) *** MATCH ***
int(0) float(0.2) NO MATCH
float(0.1) float(0.2) NO MATCH
float(0.2) float(0.2) *** MATCH ***
float(0.3) float(0.2) NO MATCH
float(0.4) float(0.2) NO MATCH
float(0.5) float(0.2) NO MATCH

我不知所措!

请问其他人可以运行此代码以查看他们是否得到相同的结果吗?

提前致谢

温度啄

标签: php

解决方案


我已将 PHP 转换为 JS,这可能有助于可视化问题:

let num1 = 0.3;
let num2 = 0.3;

if (num1 == num2) {
  console.log(`num1: ${num1} num2: ${num2} *** MATCH ***`);
} else {
  console.log(`num1: ${num1} num2: ${num2} NO MATCH`);
}

for (num1 = 0; num1 < 0.6; num1 += 0.1) {
  if (num1 == num2) {
    console.log(`num1: ${num1} num2: ${num2} *** MATCH ***`);
  } else {
    console.log(`num1: ${num1} num2: ${num2} NO MATCH`);
  }
}

这是浮点数及其存储方式的一个众所周知的问题。

这个答案特别好,因为它有助于可视化问题。

本质上,浮点数是不精确的,因为 0.3 实际上可能是 0.299999999999999999999993654 或 3.0000000000000000000001284(这不是实际值,只是问题的说明)。相互比较并不像使用==.


推荐阅读