<p>不能直接用 === 比较浮点数,因 IEEE 754 表示导致 0.1 + 0.2 === 0.3 为 false;应使用 Math.abs(a - b) < epsilon 判断近似相等。</p>

直接用 === 判断两个浮点数是否相等,常常会出错,因为浮点数在计算机中无法精确表示(比如 0.1 + 0.2 !== 0.3)。用 Math.abs 配合误差容忍值(epsilon),是更可靠的做法。
为什么不能直接用 === 比较浮点数
浮点数基于 IEEE 754 标准存储,很多十进制小数(如 0.1)在二进制下是无限循环小数,只能近似存储。运算过程中微小的舍入误差会累积,导致看似相等的计算结果实际不等。
-
0.1 + 0.2实际得到的是0.30000000000000004 -
0.3 === 0.30000000000000004返回false
用 Math.abs 实现近似相等判断
核心思路:计算两数之差的绝对值,看是否小于一个极小的阈值(即 epsilon)。这个阈值代表你愿意接受的误差范围。
- 常见 epsilon 值:
Number.EPSILON(约2.22e-16),适合比较接近 0 或 1 的数 - 对较大数值或特定场景,建议用相对误差或自定义 epsilon(如
1e-10) - 示例函数:
function floatEqual(a, b, epsilon = Number.EPSILON) {
return Math.abs(a - b) }
注意 epsilon 的选择和边界情况
固定 epsilon 不总是安全。比如比较 1000000.0000001 和 1000000.0000002,差值虽小但可能超过 Number.EPSILON;而比较 1e-20 和 0 时,Number.EPSILON 又显得太大。
立即学习“Java免费学习笔记(深入)”;
- 对数量级差异大的数,可改用相对误差:
Math.abs(a - b) - 涉及
Infinity或NaN时需单独处理(NaN与任何值都不相等,包括自身) - 简单场景用
1e-10或1e-12往往比Number.EPSILON更稳妥
实际使用建议
不要为所有数字比较都写一遍 Math.abs 逻辑。封装成可复用的工具函数,并根据业务精度要求调整 epsilon。
- 单元测试中浮点比较,推荐用测试框架内置的近似断言(如 Jest 的
toBeCloseTo) - 图形、物理模拟等对精度敏感的场景,明确记录所选 epsilon 并保持一致
- 避免在循环或高频调用中创建闭包或重复计算,优先使用常量 epsilon


















