添加到Number.MAX_VALUE

时间:2012-05-31 16:34:46

标签: javascript math floating-point infinity

这个问题的答案可能非常明显,但我无法通过粗略搜索在Mozilla文档或Google上找到它。

如果你有这样的代码

Number.MAX_VALUE + 1; // Infinity, right?
Number.MIN_VALUE - 1; // -Infinity, right?

然后我希望将任何添加到Number.MAX_VALUE会将其推送到Infinity。结果只是Number.MAX_VALUE吐了回来。

但是,在Chrome JS控制台中玩游戏时,我注意到在添加/减去之前它实际上并没有成为Infinity

Number.MAX_VALUE + Math.pow(100,1000); // now we hit Infinity
Number.MIN_VALUE - Math.pow(100,1000); // -Infinity at last

Number.MAX_VALUEInfinity之间“缓冲区”的解释是什么?

2 个答案:

答案 0 :(得分:17)

...标准方式

在ECMAScript中,添加两个非零有限数作为 (ECMA-262§11.6.3“将加法运算符应用于数字”)

  

使用 IEEE 754舍入到最接近模式计算总和并使用舍入到最接近的可表示值。如果幅度太大而无法表示,则操作溢出,结果是无穷大的适当符号。

IEEE-754的舍入到最近模式指定 (IEEE-7542008§4.3.1“舍入方向属性到最近”)

  

在以下两个舍入方向属性中,无限精确的结果,幅度至少 b emax b - ½ b 1- p )应转至∞,符号无变化;这里 emax p 由目标格式决定(见3.3)。用:

     
      
  • roundTiesToEven,最接近无限精确结果的浮点数;如果包含无法代表的无限精确结果的两个最近的浮点数同样接近,那么具有偶数最低位的数字应该被传递
  •   
  • roundTiesToAway,最接近无限精确结果的浮点数应交付;如果包含无法代表的无限精确结果的两个最接近的浮点数同样接近,则应传递幅度较大的浮点数。
  •   

ECMAScript没有指定哪一轮到最近,但这里没关系,因为两者都给出了相同的结果。 ECMAScript中的数字是“double”,其中

  • b = 2
  • emax = 1023
  • p = 53,

因此结果必须至少为2 1024 - 2 970 ~1.797693134862315 8 ×10 308 in为了圆到无穷大。否则它只会舍入到MAX_VALUE,因为 比无穷大更接近。

请注意,MAX_VALUE = 2 1024 - 2 971 ,因此您需要添加至少2 971 - 2 970 < / sup> = 2 970 ~9.979202×10 291 以获得无穷大。我们可以查一下:

>>> Number.MAX_VALUE + 9.979201e291
1.7976931348623157e+308
>>> Number.MAX_VALUE + 9.979202e291
Infinity

同时,您的Math.pow(100,1000) ~2 6643.9 远远超过2 1024 - 2 970 已经是无限的。

答案 1 :(得分:9)

如果查看Number.MAX_VALUE.toString(2),您会看到MAX_VALUE的二进制表示为53个,后跟971个零。这是因为IEEE 754浮点由尾数系数乘以2的幂(因此浮点数的另一半是指数)。使用MAX_VALUE时,尾数和指数都会被最大化,因此您会看到一堆位移了很多位。

简而言之,您需要增加MAX_VALUE足以实际影响尾数,否则您的附加值会丢失并四舍五入。

Math.pow(2, 969)是2的最低幂,不会将MAX_VALUE提示为Infinity