ES12:更可靠的 Number Parsing

在前端开发中,处理数字是非常常见的操作之一。而遇到一些输入不可靠的情况时,比如来自用户输入或者第三方数据源的字符串,如何准确地将其转换为数字就成为了一个难题。ES12 中引入了一个新的特性:更可靠的 Number Parsing,可以帮我们更方便地解决这个问题。

Number Parsing 的问题

在传统的 JavaScript 中,将字符串转换为数字一般是通过 parseIntparseFloat 来实现的。不过这些方法存在许多问题,比如:

  1. 输入不可靠parseIntparseFloat 都只会解析输入字符串的开始部分,并忽略掉结尾的非数字字符,这可能导致一些数字被误解析。

    parseInt("2.7 apples"); // 2
    parseFloat("$2.99"); // 2.99
  2. 无法检测错误:如果输入不是一个有效的数字,这些方法会返回 NaN。但它们无法告诉我们失败的原因,比如是一个类型错误、溢出、还是非法字符等。

    parseInt("foo"); // NaN
    parseInt("Infinity"); // NaN
  3. 特殊的基数参数parseInt 还有一个可选的基数参数,用于指定待解析字符串中的数字是什么进制的。但这个参数很容易被忽略或者误解。

    parseInt("010"); // 8
    parseInt("0x10"); // 16

更可靠的解析数字方法

ES12 提供了更可靠的方法来解决上述问题:BigIntNumber.parseFloat

BigInt

BigInt 是一个新的原始类型,用来表示任意精度的整数。它的实例可以通过在数字末尾加上 n 后缀来创建,也可以通过 BigInt() 函数来转换为 BigInt 类型。在解析一个数字字符串的时候,我们可以使用它的 BigInt() 函数来实现:

BigInt("100") // 100n

如果字符串不是一个有效的数字,这个方法会抛出一个 SyntaxError 异常:

BigInt("foo") // Uncaught SyntaxError: Cannot convert foo to a BigInt

通过检查抛出的异常,我们可以得知转换失败的原因。

Number.parseFloat

Number.parseFloatparseFloat 的行为类似,但它对输入的字符串做了更严格的检查。

  1. 输入必须是严格的数字格式Number.parseFloat 只会解析完全符合数字格式的字符串,而忽略掉末尾的无效字符。

    Number.parseFloat("2.7 apples"); // 2.7
    Number.parseFloat("$2.99"); // NaN
  2. 会检测错误:如果输入不是一个有效的数字,它会返回 NaN,并抛出一个 TypeError 异常。

    Number.parseFloat("foo"); // NaN, with TypeError: Not a Number
    Number.parseFloat("Infinity"); // NaN, with TypeError: Not a Number

    通过检查抛出的异常,我们可以得知转换失败的原因。

  3. 不支持进制参数Number.parseFloat 没有进制参数,因此不会出现疑惑的解析结果。

    Number.parseFloat("010"); // 10
    Number.parseFloat("0x10"); // 16

总结

ES12 中的更可靠的 Number Parsing 方法让我们能够更轻松地解析和转换数字字符串。使用 BigInt() 可以方便的将字符串转换为任意精度的整数,而 Number.parseFloat 不仅没有类型转换的陷阱,还会抛出更有意义的异常,让我们能够快速定位问题。

实现输入不可靠的数字解析时,可以优先考虑使用这些新的方法。当然,在遗留代码中的解析逻辑需要修改时,也可以替换成这些更可靠的方法。

示例代码

const input = "2.7 apples";

// 旧的解析方法
const oldParseInt = parseInt(input); // 2
const oldParseFloat = parseFloat(input); // 2.7

// 新的解析方法
const newBigInt = BigInt(input); // Uncaught SyntaxError: Cannot convert 2.7 apples to a BigInt
const newParseFloat = Number.parseFloat(input); // 2.7, with TypeError: Not a Number

来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/65942c47eb4cecbf2d8b33f1


纠错反馈