[英]Why max digits with decimal in JavaScript are only 16
不久前我在测试一些 HTML 表单时遇到了这个问题。 JavaScript Number 中带小数点的最大位数仅为 16
我已经尝试了以下
var x = 12345678912345.6789
x 是 12345678912345.68 -仅 16 位
var x = 123456789123.6789
x 是 123456789123.6789 -仅 16 位
new Number(12345678912345.6789)
12345678912345.68 -仅限 16 位数字
new Number(123456789123.6789)
123456789123.6789 -仅限 16 位数字
如果计算总位数,它们是16。如果在小数点前增加位数,则小数点后的位数会四舍五入
相似地
new Number(.12345678912367890)
是 0.1234567891236789 -仅 16 位(注意缺少尾随 0)
这让我推断出一个数字中只能有 16 位数字,其中包含小数。 如果我尝试添加更多数字,数字就会开始四舍五入
我还观察到,当我在 ASP.NET MVC 中将一个带十进制数的数字序列化为 JSoN 时,它还会将该数字转换为 Max 16 Digits 并将其余部分四舍五入
我的问题:为什么?
根据 JS/ECMAScript 规范, Number
类型使用双精度浮点,具有 64 位格式( binary64
),由一个符号位(确定正负值)、11 个指数位和 52 binary64
数位(每个数字代表4 位,因此 64 位有 16 位数字):
表示 IEEE 二进制浮点运算标准中指定的双精度 64 位格式 IEEE 754-2008 值的 Number 类型。
使用双精度可以正确表示的最大正数是9007199254740992
,这可以通过使用Math.pow(2, 53)
来实现。 如果数字范围在Math.pow(2, 53)
和Math.pow(2, 54)
之间(或在Math.pow(2, -53)
和Math.pow(2, -54)
),则只有偶数可以正确表示,因为指数位会影响小数位上的 LSB(最低有效位)。
让我们回顾一下大数部分:
var x = 12345678912345.6789
var x = new Number(12345678912345.6789)
这个数字包含超过 52 个小数位(总共 72 位),因此四舍五入用于将小数位保持为 52。
还有这个十进制数:
var x = new Number(.12345678912367890)
这个数字包含 68 个小数位,因此最后一个零被砍掉以保持 64 位长度。
通常大于9007199254740992
或小于1.1102230246251565E-16
数字表示存储为文字字符串而不是Number
。 如果您需要计算非常大的数字,可以使用某些外部库来执行任意精度算术。
进一步阅读:
在 javascript 中,您不能用二进制浮点类型(这是 ECMAScript 用来表示浮点值的)精确表示大多数小数部分。
这就是 javascript 使用小数点后 16 个数字的原因。 例如 -
尝试运行:
var x = 3.14159265358979323846;
print(x.toFixed(20));
并看到以下内容被转换为浮动。
如果你想在小数点后超过 16 点,你可以:
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.