ECMAScript 规范Math.pow
具有以下特殊规则:
- 如果 x < 0 且 x 是有限的且 y 是有限的且 y 不是整数,则结果为 NaN。
( http://es5.github.com/#x15.8.2.13 )
结果是Math.pow(-8, 1 / 3)
给出NaN
而不是-2
这个规则的原因是什么?这条规则是否有某种更广泛的计算机科学或 IEEEish 原因,或者它只是 TC39/Eich 曾经做出的选择?
更新
感谢Amadan与我的交流,我想我现在明白了其中的道理。为了后代,我想扩展我们的讨论。
让我们看下面的例子:Math.pow(823543, 1 / 7)
虽然6.999999999999999
它确实应该是7
. 这是由于1 / 7
必须首先转换为十进制表示而导致的不准确性0.14285714285714285
,该表示被截断并失去精度。当我们使用正数时,这并不是一个糟糕的问题,因为我们仍然会得到非常接近真实结果的结果。
然而,一旦我们踏入消极的世界,我们就会遇到问题。如果一个 JavaScript 引擎要尝试计算Math.pow(-823543, 1 / 7)
,它首先需要转换1 / 7
为小数,所以它Math.pow(-823543, 0.14285714285714285)
实际上是没有真正答案的计算。在这种情况下,它可能不得不返回,NaN
因为它找不到实数,即使真正的答案应该是-7
。此外,寻找接近实数的复数以进行“最佳猜测”可能涉及一定程度的复杂性,他们不希望在数学领域中需要 JS 引擎。
我的猜测是由于考虑到浮点数的精度损失,导致他们得出这样的规则:负数的非整数幂应该总是NaN
——基本上是因为非整数幂可能会给出由于精度损失而导致的复数,即使它不应该,并且可能没有好的方法可以从中恢复。
对此,我相当满意,但我欢迎进一步的信息。