本文深入解析 JavaScript 中的 Infinity 全局属性,涵盖其作为正无穷大的定义、与 -Infinity 的区别、数学运算行为及与 BigInt 的兼容性问题。重点介绍如何正确检测无穷数,并详细阐述 Infinity 在 Math.max/min、JSON 序列化及字符串解析中的特殊表现与潜在陷阱,帮助开发者避免常见错误。
前言
在 JavaScript 中,Infinity 是一个特殊的数值属性,可赋值给任意变量以表示无穷大。本文将详细解析 Infinity 的工作机制及其在实际开发中需要注意的关键事项。
1. Infinity 概念
Infinity 是全局对象的一个属性,即它是一个全局变量:
console.log(window.Infinity); // Infinity
console.log(window.Infinity > 100); // true
console.log(window.Infinity < 100); // false
Infinity 的初始值等于 Number.POSITIVE_INFINITY。该值大于任何有限数值,其行为符合数学中无穷大的定义。例如,任何正数乘以 Infinity 仍为 Infinity,而任何有限数字除以 Infinity 则结果为 0。根据 ECMAScript 5 规范,Infinity 是只读属性,不可被重写、枚举或配置。
在 JavaScript 中,Infinity 是一个特殊数值,其近似值为 1.79e+308 或 2¹⁰²⁴,这代表了 JavaScript 中 Number 类型所能存储的最大值。
let bigNumber = 1e308,
biggerNumber = 1e309;
console.log(bigNumber); // 1e+308
console.log(biggerNumber); // Infinity依据规范,任何大于 1.7976931348623157e+308 的数值将被表示为 Infinity:
let largeNumber = 1.7976931348623157e+308,
largerNumber = 1.7976931348623157e+309;
console.log(largeNumber); // 1.7976931348623157e+308
console.log(largerNumber); // Infinity我们可以在浏览器的控制台输入9,当输入308位时,结果还是1e+308,当输入309位时,就会打印出 Infinity:
所有主流浏览器均支持 Infinity 属性:
2. Infinity 正负
Infinity 具有正负之分:Infinity 表示正无穷大,而 -Infinity 表示负无穷大。具体而言,大于 1.797693134862315E+308 的数值即为 Infinity,而小于 -1.797693134862316E+308 的数值则为 -Infinity。
console.log(1.7976931348623157e+309); // Infinity
console.log(-1.7976931348623157e+309); // -Infinity
可以通过以下方式来得到 Infinity:
console.log(Infinity) // Infinity
console.log(Number.POSITIVE_INFINITY) // Infinity
console.log(Math.pow(2,1024)) // Infinity
console.log(1.8e+308) // Infinity
console.log(1/0) // Infinity
可以通过以下方式来得到 -Infinity:
console.log(-Infinity) // -Infinity
console.log(Number.NEGATIVE_INFINITY) // -Infinity
console.log(-1*Math.pow(2,1024)) // -Infinity
console.log(-1.8e+308) // -Infinity
console.log(1/-0) // -Infinity
将正数除以 Infinity 会得到 0;Infinity 除以 Infinity 会得到 NaN;正数除以 -Infinity 或负数除以 Infinity 则得到 -0:
console.log(1/Infinity) // 0
console.log(Infinity/Infinity) // NaN
console.log(1/-Infinity) // -0
3. Infinity 计算
Infinity 的行为在加、减、乘运算中类似于数学无穷大,结果仍为 Infinity:
console.log(Infinity + 3) // Infinity
console.log(Infinity - 3) // Infinity
console.log(Infinity * 3) // Infinity
console.log(Infinity / 3) // Infinity
console.log(Math.pow(Infinity, 2)) // Infinity
console.log(Infinity + Infinity) // Infinity
console.log(Infinity - Infinity) // NaN
console.log(Infinity * Infinity) // NaN
console.log(Infinity / Infinity) // NaN对于 JavaScript 中的所有数字,即使是 Infinity,若与 NaN 进行数学运算,结果均为 NaN:
console.log(Infinity + NaN) // NaN
console.log(Infinity - NaN) // NaN
console.log(Infinity * NaN) // NaN
console.log(Infinity / NaN) // NaN
console.log(Math.pow(Infinity, NaN)) // NaN4. Infinity 和 BigInt
JavaScript 提供了 BigInt 原始类型以处理任意大的整数值。然而,BigInt 与 Infinity 的兼容性较差,因为 Infinity 属于 number 类型,两者不能直接混合使用。
try{console.log(37/0)} catch(e) {console.log(e)} // Infinity
// BigInts 用数字后面的 n 表示:
try{console.log(37n/0)} catch(e) {console.log(e)} // TypeError: "can't convert BigInt to number"
try{console.log(37/0n)} catch(e) {console.log(e)} // TypeError: "can't convert BigInt to number"
try{console.log(37n/0n)} catch(e) {console.log(e)} // RangeError: "BigInt division by zero"
// 可以将 BigInts 转换为 Numbers:
try{console.log(Infinity+37n)} catch(e) {console.log(e)} // TypeError: "can't convert BigInt to number"
try{console.log(Infinity+Number(37n))} catch(e) {console.log(e)} // Infinity
// 可能不需要BigInts,因为它可以是任意大小,并且 JavaScript 中的最大安全整数只有 16 位长:
console.log(Number.MAX_SAFE_INTEGER) // 90071992547409915. Infinity 检查
可以使用 == 或 === 运算符将值与 Infinity 进行比较以进行检查:
console.log(Infinity == 1/0) // true
console.log(Infinity === 1/0) // true
// ==将强制字符串转换为数字,但===不会:
console.log(Infinity == "Infinity") // true
console.log(Infinity === "Infinity") // false
// 使用除法运算符将在比较之前强制执行强制转换:
console.log(Infinity == "1"/"0") // true
console.log(Infinity === "1"/"0") // true
// 当强制转换后值为NaN时:
console.log(Infinity == "1/0") // false
console.log(Infinity === "1/0") // false在处理 Infinity 时,ES6 引入的 Object.is() 与 === 运算符的行为一致:
console.log(Object.is(Infinity, 1/0)) // true
console.log(Infinity === 1/0) // true
console.log(Infinity == 1/0) // true
console.log(Object.is(Infinity, "Infinity")) // false
console.log(Infinity === "Infinity") // false
console.log(Infinity == "Infinity") // true可以使用辅助函数 Number.isFinite() 来检查值是否为有限数(即排除 Infinity、-Infinity 或 NaN)。此外,还有一个全局函数 isFinite(),它会执行强制类型转换,即先尝试将值转换为数字类型,然后再检查其是否为有限数。
console.log(isFinite(45)); // true
console.log(isFinite(-45)); // true
console.log(isFinite('45')); // true
console.log(isFinite('-75')); // true
console.log(isFinite(Infinity)); // false
console.log(isFinite(1.7976931348623157e+308)); // true
console.log(isFinite(1.7976931348623157e+309)); // false
6. 注意事项
(1)max() 和 min()
如果未传入参数,Math.max()(返回传入值中的最大值)将返回 -Infinity,而 Math.min()(返回传入值中的最小值)将返回 Infinity。
console.log(Math.max()); // -Infinity
console.log(Math.min()); // Infinity
(2)Infinity 作为默认值
由于 Infinity 大于所有有限数字,它在用于查找数组中最小数字的函数中非常有用:
function findMinimum(numbers) {
let min = Infinity;
for (const n of numbers) {
if (n < min) {
min = n
};
}
return min;
}
console.log(findMinimum([20, 6, 90])); // 6因为 Infinity 大于所有数字,所以除非数组中的所有数字都超过 Infinity 阈值(这在有限数中不可能发生),否则结果不会有任何问题。
(3)转换为 JSON 时
在处理 JSON 数据时,如果使用 JSON.stringify() 将 JavaScript 对象转换为有效的 JSON 字符串,Infinity 将会被转化为 null:
let myJSON = {
value1: 6,
value2: 'Example',
value3: Infinity,
value4: -Infinity,
value5: 1.7976931348623157e+309
};
console.log(JSON.stringify(myJSON, null, 2));打印结果如下:
{ "value1": 6, "value2": "Example", "value3": null, "value4": null, "value5": null }
(4)parseFloat() 和 parseInt()
parseFloat() 用于解析字符串并返回浮点数,parseInt() 用于解析字符串并返回整数。parseFloat() 可以正确解析 Infinity,而 parseInt() 无法识别 Infinity:
总结
到此这篇关于JavaScript中Infinity(无穷数)的文章就介绍到这了,更多相关js的无穷数Infinity内容请搜索本站以前的文章或继续浏览下面的相关文章希望大家以后多多支持本站!