lodash的toNumber和parseInt之间有什么区别?

4

我知道Lodash通常会在JavaScript已有的函数中添加一些额外的检查或美化操作,但是不清楚_.toNumber具体做了什么,以至于我不能用parseInt来代替它。

我更喜欢只在Lodash提供的好处在现有的JavaScript函数中不存在时使用它,但在这种情况下我看不出有任何好处。

2个回答

19

我认为直接查看_.toNumber源代码就可以回答你的问题:

function toNumber(value) {
  if (typeof value == 'number') {
    return value;
  }
  if (isSymbol(value)) {
    return NAN;
  }
  if (isObject(value)) {
    var other = typeof value.valueOf == 'function' ? value.valueOf() : value;
    value = isObject(other) ? (other + '') : other;
  }
  if (typeof value != 'string') {
    return value === 0 ? value : +value;
  }
  value = value.replace(reTrim, '');
  var isBinary = reIsBinary.test(value);
  return (isBinary || reIsOctal.test(value))
    ? freeParseInt(value.slice(2), isBinary ? 2 : 8)
    : (reIsBadHex.test(value) ? NAN : +value);
}

正如您所看到的,与 parseInt 相比,它还执行了许多其他操作。 更具体地说:

console.log(_.toNumber(1),       parseInt(1))        // same 
console.log(_.toNumber('1'),     parseInt('1'))      // same  
console.log(_.toNumber('b'),     parseInt('b'))      // same  
console.log(_.toNumber({}),      parseInt({}))       // same 
console.log(_.toNumber(' 1 '),   parseInt(' 1 '))    // same
console.log(_.toNumber([1]),     parseInt([1]))      // same
console.log(_.toNumber(' 1a1 '), parseInt(' 1a1 '))  // NaN      1
console.log(_.toNumber([1,2]),   parseInt([1,2]))    // NaN      1
console.log(_.toNumber(false),   parseInt(false))    // 0        NaN
console.log(_.toNumber(!0),      parseInt(!0))       // 1        NaN
console.log(_.toNumber(!!0),     parseInt(!!0))      // 0        NaN
console.log(_.toNumber(5e-324),  parseInt(5e-324))   // 5e-324   5
console.log(_.toNumber(5.5),     parseInt(5.5))      // 5.5      5
console.log(_.toNumber(null),    parseInt(null))     // 0        NaN
console.log(_.toNumber(Infinity),parseInt(Infinity)) // Infinity NaN
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>

总之,_.isNumber 在解析包含数组、小数、假值和字符串的输入时,提供了更多的期望/一致性,而且我认为结果也更加安全。相比之下,parseInt只关心第一个有效值,可以从上面的示例中看到。它还更好地处理否定运算符(!)等。

总的来说,与parseInt相比,它确实有其用处。

注意:这里需要注意的是,_.toNumberparseInt都会针对undefined返回NaN。考虑到_.toNumber如何处理其余的假值,人们可能预期返回0而不是NaN

console.log(_.toNumber(undefined), parseInt(undefined))  // NaN NaN

1
好主意,一开始我就应该检查源代码的。对于未来像这样的lodash问题,我会这样做,因为我总是这样想。 - Brady Dowling
我想对上面的答案提出更正建议。我认为说lodash toNumber可以给出更符合预期的结果可能会误导人。请在您的示例中添加以下值: 10% 100美元 100美元或任何其他货币字符。parseInt和parseFloat都按照预期处理它们,而toNumber返回NaN。 - Nevararn

3

_.toNumber 将给定的输入转换为数字,如果无法进行转换,则返回NaNparseIntparseFloat 方法也以同样的方式运作(前者只返回整数),但是它们在解析规则方面要宽松得多。 _.toNumber 更加严格。

例如,对于相同的输入'5.2a'parseInt将返回5parseFloat将返回5.2,而_.toNumber将返回NaN。前两个方法忽略第一个未被识别的字符之后的所有内容,并返回到该点为止解析的所有字符组成的数字。然而最后一个方法会在遇到未被识别的字符时返回NaN。

_.toNumberNumber 函数相当且功能相同。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接