我在 PHP 和 NodeJS 中执行了相同的添加。 PHP 最多可正确计算 10 亿次迭代,但 NodeJS 最多只能正确计算 1 亿次迭代。
这是 PHP 代码:
<?php
$start_time = time();
$j = 0;
for ($i = 0; $i <= 1000000000; $i++) {
$j += $i;
}
$end_time = time();
echo "Time Taken: " . ($end_time - $start_time);
echo "\n";
echo "i: " . $i;
echo "\n";
echo "j: " . $j;
echo "\n";
?>
返回以下输出:
Time Taken: 15
i: 1000000001
j: 500000000500000000
这是 NodeJS 代码:
var epoch = require('epoch.js');
var start_time = epoch().format('ss');
var i;
var j = 0;
for (i = 0; i <= 1000000000; i++) {
j += i;
}
var end_time = epoch().format('ss');
var time_taken = end_time - start_time;
console.log("Time Taken: " + time_taken + " \ni: " + i + "\nj: " + j);
返回以下输出:
Time Taken: 1
i: 1000000001
j: 500000000067109000
为什么NodeJS中的j
变量是错误的?
编辑:
正如@SalmanA 所指出的(并经我证实),我还想问一下,为什么最大整数限制对于不同处理器上的 Javascript 保持不变,但对于 PHP 却有所变化?
最佳答案
既然你改变了问题的意图,我想重新打开它。
在 JavaScript 中,没有整数或 float ,只有 Number
,使用 IEEE 754-2008 64 位( double )格式表示。这种格式的特点之一是可以准确表示-9007199254740991和9007199254740991之间的所有“整数”。超出此范围的数字是近似值。简单示例:
> 9007199254740993
< 9007199254740992
您的 Node.js 代码生成的值大于 Number.MAX_SAFE_INTEGER
,这就是结果是近似值而不是准确值的原因。
在 PHP 中,你有 integers and floats .然而:
- 整数数据类型的大小在所有平台上都不相同
- PHP x64 使用 8 字节整数*(-9223372036854775808 ... 9223372036854775807)
- PHP x86 使用 4 字节整数(-2147483648 ... 2147483647)
- PHP 似乎 使用 IEEE 754-2008 64 位 float ,与 JavaScript 相同
- PHP 将变量的数据类型从整型更改为浮点型以防溢出
您的示例程序在 PHP x64 上运行时以 $j = int(500000000500000000)
结束,它小于 PHP_INT_MAX
的值,因此转换为 float(和精度损失)不会发生。
相同的代码,当在 PHP x86 上运行时,一旦变量大于 PHP_INT_MAX
就会将变量转换为浮点值,因此您将以 $ 结尾j = float(5.0000000006710899E+17)
**.
* 虽然不是在 Windows 上
** 你需要将 precision
设置为最大值
关于javascript - 为什么 NodeJS 对大数加法不准确?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48295347/