返回

JS中超出安全整数范围精度丢失的问题

前端

8月更文挑战第一弹,你准备好了吗?

在 JavaScript 中,安全整数范围是 -2^53 到 2^53-1,超出这个范围会导致精度丢失。这是因为 JavaScript 使用 64 位浮点数来表示数字,而浮点数不能精确表示所有整数。

例如,以下代码将输出 1.0000000000000002:

console.log(1 + 0.1);

这是因为 0.1 不能被精确表示为二进制小数,因此当它与 1 相加时,结果是一个近似值。

精度丢失可能会导致意外的结果。例如,以下代码将输出 false:

console.log(1000000000000000000 === 1e20);

这是因为 1000000000000000000 是一个安全整数,而 1e20 是一个浮点数。即使它们的值相同,但由于精度丢失,它们并不相等。

为了避免精度丢失,可以使用以下方法:

  • 使用 BigInt 类型。BigInt 类型可以表示比安全整数范围更大的整数。
  • 使用 Math.round()、Math.floor() 或 Math.ceil() 函数来舍入数字。
  • 使用 parseInt() 或 parseFloat() 函数来将字符串转换为整数或浮点数。

在使用这些方法时,需要注意以下几点:

  • BigInt 类型不支持所有操作。例如,不能将 BigInt 类型与其他类型的值进行比较。
  • Math.round()、Math.floor() 和 Math.ceil() 函数可能会改变数字的值。
  • parseInt() 和 parseFloat() 函数可能会返回一个错误值,如果字符串不能被转换为整数或浮点数。

示例代码

// 使用 BigInt 类型
const bigInt = 1000000000000000000n;

// 使用 Math.round() 函数
const rounded = Math.round(1.0000000000000002);

// 使用 parseInt() 函数
const integer = parseInt('1000000000000000000');

// 使用 parseFloat() 函数
const floatingPoint = parseFloat('1.0000000000000002');

// 输出结果
console.log(bigInt); // 1000000000000000000
console.log(rounded); // 1
console.log(integer); // 1000000000000000000
console.log(floatingPoint); // 1.0000000000000002

总结

在 JavaScript 中,安全整数范围是 -2^53 到 2^53-1,超出这个范围会导致精度丢失。为了避免精度丢失,可以使用 BigInt 类型、Math.round()、Math.floor() 或 Math.ceil() 函数、parseInt() 或 parseFloat() 函数。