JavaScript 中的最大整数值
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/21350175/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
max integer value in JavaScript
提问by Emil A.
I'm reading the second chapter of the book Eloquent JavaScript. The author states that:
我正在阅读Eloquent JavaScript 一书的第二章。作者指出:
Any whole number less than 2^52 (which is more than 10^15) will safely fit in a JavaScript number.
Any whole number less than 2^52 (which is more than 10^15) will safely fit in a JavaScript number.
I grabbed the value of 2^52 from wikipedia.
我从wikipedia 中获取了 2^52 的值。
4,503,599,627,370,496
4,503,599,627,370,496
The value has to be less than 2^52, so I've substracted 1 from the initial value;
该值必须小于 2^52,所以我从初始值中减去了 1;
var max = 4503599627370495;
After defining the max variable I'm checking what's the value (I'm using Chrome 32.0.1700.77
).
定义 max 变量后,我正在检查值是什么(我正在使用Chrome 32.0.1700.77
)。
console.log(max); // 4503599627370495
I'd like to see what happens when I go over this limit, so I'm adding one a couple of times.
我想看看当我超过这个限制时会发生什么,所以我添加了几次。
Unexpectedly:
不料:
max += 1;
console.log(max); // 4503599627370496
max += 1;
console.log(max); // 4503599627370497
max += 1;
console.log(max); // 4503599627370498
I went over the limit and the calculations are still precise.
我超过了限制,计算仍然精确。
I tried the next power of two instead, 2^53, I didn't substract 1 this time:
我尝试了下一个 2 的幂,2^53,这次我没有减去 1:
9,007,199,254,740,992
9,007,199,254,740,992
var max = 9007199254740992;
This one seems to be a bigger limit, it seems that I can quite safely add and substract numbers:
这似乎是一个更大的限制,似乎我可以相当安全地加减数字:
max += 1;
console.log(max); // 9007199254740992
max += 1;
console.log(max); // 9007199254740992
max -= 1;
console.log(max); // 9007199254740991
max += 1;
console.log(max); // 9007199254740992
max -= 900;
console.log(max); // 9007199254740092
max += 900;
console.log(max); // 9007199254740992
I can assign even a bigger value to the max, however it loses precision and I can't safely add or substract numbers again.
我可以为最大值分配更大的值,但是它会失去精度并且我无法再次安全地添加或减去数字。
Could you please explain precisely the mechanism that sits under the hood? An example of what happens with the bits after going above 2^52 would be really helpful.
你能准确解释一下引擎盖下的机制吗?超过 2^52 后位发生的情况的示例将非常有帮助。
采纳答案by Arthur Yakovlev
This is not a strongly typed programming language. JS has an object Number
. You can even get an infinite number: document.write(Math.exp(1000));
.
这不是强类型编程语言。JS 有一个对象Number
。你甚至可以得到一个无限的数字:document.write(Math.exp(1000));
。
document.write(Number.MIN_VALUE + "<br>");
document.write(Number.MAX_VALUE + "<br>");
document.write(Number.POSITIVE_INFINITY + "<br>");
document.write(Number.NEGATIVE_INFINITY + "<br>");
alert([
Number.MAX_VALUE/(1e293),
Number.MAX_VALUE/(1e292),
Number.MAX_VALUE/(1e291),
Number.MAX_VALUE/(1e290),
].join('\n'))
Hope it's a useful answer. Thanks!
希望这是一个有用的答案。谢谢!
UPDATE:max int is - +/- 9007199254740992
更新:最大整数是 - +/- 9007199254740992
回答by Siegfried Gevatter
You can find some information on JavaScript's Number type here: ECMA-262 5th Edition: The Number Type.
您可以在此处找到有关 JavaScript 数字类型的一些信息:ECMA-262 第 5 版:数字类型。
As it mentions, numbers are represented as a 64-bit floating-point number, with 53 bits of mantissa (significant digits) and 11 bits for the exponent (IEEE 754). The result is then obtained with: mantissa * 2^exponent.
正如它所提到的,数字表示为 64 位浮点数,尾数为 53 位(有效数字),指数为 11 位(IEEE 754)。然后通过以下方式获得结果:尾数 * 2^指数。
This means that up to 2^53 values can be represented in the mantissa (of those a few numbers have special meanings, and the others are positive and negative integers).
这意味着尾数中最多可以表示 2^53 个值(其中少数数字具有特殊含义,其余为正整数和负整数)。
The number 2^53 (9007199254740992) can't be represented in the mantissa, and you have to use an exponent. As an example, you can represent 2^53 as (9007199254740992 / 2) * 2^1
, ie. mantissa = 9007199254740992 / 2 = 4503599627370496
and exponent = 1
.
数字 2^53 (9007199254740992) 不能用尾数表示,必须使用指数。例如,您可以将 2^53 表示为(9007199254740992 / 2) * 2^1
,即。mantissa = 9007199254740992 / 2 = 4503599627370496
和exponent = 1
。
Let's check what happens with 2^53+1 (9007199254740993). Here we have to do the same, mantissa = 9007199254740993 / 2 = 4503599627370496
. Oops, isn't this the same mantissa we had for 2^53? Looks like there's been some rounding error! :)
让我们来看看 2^53+1 (9007199254740993) 会发生什么。在这里,我们必须做同样的事情,mantissa = 9007199254740993 / 2 = 4503599627370496
。哎呀,这不是我们 2^53 的尾数吗?看起来有一些舍入错误!:)
(Note: the above examples are not actually how it really works: the mantissa is always interpreted as having a dot after the first digit, which means that eg. the number 3 is actually stored as 1.5*2
. I omitted this in the above explanation to make it easier to follow.)
(注意:上面的例子实际上并不是它的实际工作原理:尾数总是被解释为在第一个数字后面有一个点,这意味着例如数字 3 实际上存储为1.5*2
。我在上面的解释中省略了这一点,以便更容易遵循。)
You can find some more information on floating-point numbers (in general) here: What Every Computer Scientist Should Know About Floating-Point Arithmetic.
您可以在此处找到有关浮点数(一般)的更多信息:What Every Computer Scientist should Know About Floating-Point Arithmetic。
回答by exebook
You can think of 52 bits integer in JS, but remember that bitwise logical operators &
|
>>
etc.. will only deal with 32 less significant bits discarding the rest.
您可以在 JS 中想到 52 位整数,但请记住,按位逻辑运算符&
|
>>
等只会处理 32 位较低的有效位,而丢弃其余的位。