[英]Strange JavaScript Number behavior
I found the following weird behavior while working on JavaScript numbers. 在处理JavaScript数字时,我发现了以下奇怪的行为。
var baseNum = Math.pow(2, 53);
console.log(baseNum); //prints 9007199254740992
console.log(baseNum + 1); //prints 9007199254740992 again!
console.log(baseNum + 2); //prints 9007199254740994, 2 more than +1
console.log(baseNum + 3) // prints 9007199254740996, 2 more than +2
console.log(baseNum + 4) // prints 9007199254740996, same as +3
What is happening here? 这里发生了什么? I understand that JavaScript can only represent numbers upto
2^53
(they are internally 'double'?), but why this behavior? 我理解JavaScript只能代表高达
2^53
数字(它们内部是'双'?),但为什么会出现这种情况呢?
If 2^53
is the practical max, then why do we have Number.MAX_VALUE
( 1.7976931348623157e+308
)?. 如果
2^53
是实际最大值,那么为什么我们有Number.MAX_VALUE
( 1.7976931348623157e+308
)?
The number is really a double. 这个数字确实是一个双倍。 The mantissa has 52-bits ( source and extra information on doubles ).
尾数有52位( 关于双精度的源和额外信息 )。 Therefore, storing 2^53 chops off the one bit.
因此,从一位存储2 ^ 53个剁。
The number is stored using 3 pieces a sign bit (fairly straight forward) and two other pieces, the mantissa M and the exponent E. The number is calculated as: 使用3个符号位(相当直接)和另外两个部分(尾数M和指数E)存储该数字。该数字计算如下:
(1 + M/2^53) * 2^(E-1023) (1 + M / 2 ^ 53)* 2 ^(E-1023)
I might have some of the specifics there a little off, but the basic idea is there. 我可能会有一些细节,但基本的想法就在那里。 So when the number is 2^53, 2^(E-1023) = 2^53 and since there are only 52 bits in M, you can no longer represent the lowest bit.
因此当数字是2 ^ 53,2 ^(E-1023)= 2 ^ 53并且因为M中只有52位,所以你不能再代表最低位。
The answer that @CrazyCasta gave is good. @CrazyCasta给出的答案很好。
The only thing to add is to your second question: 唯一要补充的是你的第二个问题:
If
2^53
is the practical max, then why do we haveNumber.MAX_VALUE
(1.7976931348623157e+308
)?如果
2^53
是实际最大值,那么为什么我们有Number.MAX_VALUE
(1.7976931348623157e+308
)?
As you've demonstrated, it can store numbers larger than 2^53
, but with precision worse than 2^0
. 如您所示,它可以存储大于
2^53
数字,但精度低于2^0
。 As the numbers grow ever larger, they lose more and more precision. 随着数字越来越大,它们失去了越来越多的精确度。
So max value in Number.MAX_VALUE
means the "largest" value it can represent; 因此,
Number.MAX_VALUE
中的Number.MAX_VALUE
表示它可以表示的“最大”值; but it doesn't mean that accuracy is the same as a value near 2^1
or 2^53
. 但这并不意味着准确度与
2^1
或2^53
附近的值相同。
A corollary to this is that Number.MIN_VALUE
is the smallest value that Number can contain; 对此的推论是
Number.MIN_VALUE
是Number可以包含的最小值 ; not the most negative . 不是最消极的 。 That is, it is the closest non-zero number to zero:
5.00E-324
(notice that's a positive number!). 也就是说,它是最接近零的非零数字:
5.00E-324
(注意这是一个正数!)。
The maximum value storable in a long is much larger than the maximum value storable with exact precision in a long. 长度可存储的最大值远大于可存储的最大值,精确度可长。 Floating-point numbers have a fixed maximum number of significant digits, but the magnitude of the number can get much larger.
浮点数具有固定的最大有效位数,但数字的大小可以变得更大。
There are a certain number of bits allocated for an exponent (power of two), and that's implicitly multiplied by the mantissa stored in the rest of the bits. 为指数分配了一定数量的比特(2的幂),并且隐含地乘以存储在其余比特中的尾数。 Beyond a certain point, you lose precision, but you can keep incrementing the exponent to represent larger and larger magnitudes.
超过某一点,你会失去精确度,但你可以继续递增指数来表示更大和更大的数量级。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.