Loading [MathJax]/jax/input/TeX/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >专栏 >JavaScript中科学计数法的问题

JavaScript中科学计数法的问题

作者头像
用户2192970
发布于 2019-08-18 05:43:42
发布于 2019-08-18 05:43:42
12.5K00
代码可运行
举报
文章被收录于专栏:杨飞@益术杨飞@益术
运行总次数:0
代码可运行

JavaScript 中经常会碰到数值计算问题,偶尔会在不经意间报一个不是bug的bug。今天来说说一个特殊的例子。我以0.0011BTC 价格买入 0.0002CZR 计算出了的金额是 0.00000022BTC,而 JavaScript 计算出来的金额是 2.2e-7 。值是对的,只是用了科学计数法,也是数值类型。但是问题来了,一般用户用户看不懂 2.2e-7,那么就把它转换成 0.00000022 吧。然而问题了,我用尽办法,怎么样都无法将 2.2e-7 转换成直观的 0.00000022。或许你会嘲笑我,告诉我直接用 .toFixed() 方法。但是新问题又来了, .toFixed() 会保留足够的小数位,比如:2e-7.toFixed(8) 得到的值是 0.000000202e2.toFixed(8)得到的值是 200.00000000。最后的 0 让我感到多余…

问题分析

问题还是要解决,只能深入了解 JavaScript 中科学计数法相关的知识。对于极大或者极小的数,可以用科学计数法 e来表示的浮点数值来表示。科学计数法允许字母eE 的后面,跟着一个整数,表示这个数值的指数部分。

以下两种情况,JavaScript 会自动将数值转为科学计数法表示

(1) 小于1且小数点后面带有6个0以上的浮点数值:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
0.0000003 // 3e-7
0.00000033 // 3.3e-7
0.000003 // 0.000003

(2) 整数位数字多于21位:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
1234567890123456789012 //1.2345678901234568e+21
1234567890123456789012.1 //1.2345678901234568e+21
123456789012345678901 //123456789012345680000

解决思路

首先看看整数位数字多于21位的情况,其实这个一般不会碰到,整数位数字多于21位已经超出了 JavaScript 精确整数范围 ?9007199254740992 至 9007199254740992 (即正负2的53次方)。如果你需要可以是使用 bignumber.js。一般情况你可以使用.toString() 将科学计数法的数字转化为直观的数字表示,例如:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
""+1.401e10 // "14010000000"
1.401e10.toString(10) // "14010000000"

小于1且小数点后面带有6个0以上的浮点数值自动转化为科学计数法,要想转换成直观的数字表示就没那么容易了,我尝试了几种办法:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
""+3.3e-7 //"3.3e-7"
3.3e-7.toString(10) //"3.3e-7"

都没达到我的预期。

解决问题

精度计算的时候我们通常会使用 .toFixed() 方法,Number.toFixed(digits) 方法使用定点表示法来格式化一个数,会对结果进行四舍五入。参数 digits 表示小数点后数字的个数,一般介于 0 到 20 (包括)之间。例如:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
3.3e-7.toFixed(8); // "0.00000033"
3e-7.toFixed(8); // "0.00000030"

一般情况下,我们的需求小数位数是固定的,所以这个基本可以满足我们的需求。但是有些人可能不喜欢 0.00000030 这种形式,认为最后的 0 是多余的。所以索性就改进了一下:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function toNumberStr(num,digits) {
// 正则匹配小数科学记数法
if (/^(\d+(?:\.\d+)?)(e)([\-]?\d+)$/.test(num)) {
// 正则匹配小数点最末尾的0
var temp=/^(\d{1,}(?:,\d{3})*\.(?:0*[1-9]+)?)(0*)?$/.exec(num.toFixed(digits)) ;
if(temp){
return temp[1];
}else{
return num.toFixed(digits)
}
}else{
return ""+num
}
}
 
toNumberStr(3.3e-7,8) // "0.00000033"
toNumberStr(3e-7,8) // "0.0000003"
toNumberStr(1.401e10,8) // "14010000000"
toNumberStr(0.0004,8) // "0.0004"

这个方法基本满足了我的需求,但是总是觉得一点累赘,后面那个参数意思也不够明确,所以发到微信群请大家帮忙优化。特别感谢网友 @caikan 提供的方法:

JavaScript 代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function toNonExponential(num) {
var m = num.toExponential().match(/\d(?:\.(\d*))?e([+-]\d+)/);
return num.toFixed(Math.max(0, (m[1] || '').length - m[2]));
}
toNonExponential(3.3e-7) // "0.00000033"
toNonExponential(3e-7) // "0.0000003"
toNonExponential(1.401e10) // "14010000000"
toNonExponential(0.0004) // "0.0004"

解析一下:

.toExponential()将数字转化为科学记数法表示,匹配正则表达式/\d(?:\.(\d*))?e([+-]\d+)/,获取科学记数法中小数点后的字符及幂指数(e 后面的值),这样可以确定数字是几位小数。再用toFixed()转换成数值表示。

转自:https://www.html.cn/archives/9318

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2019年07月30日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
Js中Number对象
JavaScript的Number对象是经过封装从而能够处理数字值的对象,Number对象由Number()构造器以及字面量声明的值在转化为包装对象时创建,JavaScript的Number类型为双精度IEEE 754 64位浮点类型。
WindRunnerMax
2020/10/10
3.5K0
JavaScript 浮点数陷阱及解法
众所周知,JavaScript 浮点数运算时经常遇到会 0.000000001 和 0.999999999 这样奇怪的结果,如 0.1+0.2=0.30000000000000004、1-0.9=0.09999999999999998,很多人知道这是浮点数误差问题,但具体就说不清楚了。本文帮你理清这背后的原理以及解决方案,还会向你解释JS中的大数危机和四则运算中会遇到的坑。
laixiangran
2018/10/22
1.8K0
JavaScript 浮点数陷阱及解法
[第34期] 彻底搞懂Javascript 浮点数
前言 前段时间, 在群里跟 Peter 说到JS的浮点数问题。 他问我, 为什么 0.1 + 0.2 !== 0.3, 而 0.05 + 0.25 === 0.3 ? 当时也大概解释了下是精度丢失,
皮小蛋
2020/03/02
1.7K0
抓住数据的小尾巴 - JS 浮点数陷阱及解法 camsong
链接 | https://zhuanlan.zhihu.com/p/30703042
五月君
2019/10/29
2.5K0
抓住数据的小尾巴 - JS 浮点数陷阱及解法 camsong
一篇文章带你了解JavaScript 数值方法(上篇)
可以使用内置方法和属性对数字执行哪些有用的操作。原始值,例如(25或3.14),不能具有属性或方法(因为它们不是对象)。
前端进阶者
2021/01/22
5820
如何判断字符串是不是数字
在编程的世界里,验证用户输入是否符合预期格式,是常见又必要的一环。一个常见的验证场景,就是检查某个字符串是否表示一个有效的数字。今天我们就来看看,如何用 Java 判断一个字符串是不是合法的数字格式。
FunTester
2025/04/24
830
如何判断字符串是不是数字
使用js,对数值保留小数点后两位的处理(两种情况)
// 情况二:保留小数点后两位的过滤器,尾数不四舍五入(此处存在一个问题,当源数据小数点第三位为数字9,并且第四位会导致第三位进位的情况下,得到的最终数据仍然不是截取 eg: 3.1798 截取两位会变成3.18)
全栈程序员站长
2022/08/26
2.6K0
JavaScript的理解记录(1)
原始类型包括:数字,字符串,布尔值,null和undefined; (都是不可变类型,值不可以修改)
JQ实验室
2022/02/09
6390
JavaScript数值
JavaScript 只有一种数值类型,书写数值时带不带小数点均可。超大或超小的数可通过科学计数法来写。
hotarugali
2022/03/01
9800
qDebug避免科学计数法打印
  由于qDebug底层使用QTextStream打印数据,而QTextStream可以设置输出的格式为科学计数法。qDebug不提供设置浮点型数据输出为定点记数法,只能通过其他方式解决。
Qt君
2020/04/01
3K0
四舍六入,五看奇偶
一个数值的字符串表现形式,不使用指数记数法,而是在小数点后有 digits 位数字。该数值在必要时进行四舍五入,另外在必要时会用 0 来填充小数部分,以便小数部分有指定的位数。 如果数值大于 1e+21,该方法会简单调用 Number.prototype.toString()并返回一个指数记数法格式的字符串。
用户7293182
2022/01/13
4650
四舍六入,五看奇偶
JavaScript 数据类型转换完全攻略
JavaScript 能够根据运算环境自动转换值的类型,以满足运算需要。但是在很多情况下需要开发者手动转换数据类型,以控制运算过程。
用户3519280
2023/07/07
3340
string类型保留两位小数_js保留4位小数
第一种,先把小数边整数:Math.floor(15.7784514000 * 100) / 100
全栈程序员站长
2022/09/23
8.9K0
《Java从入门到失业》第三章:基础语法及基本程序结构(3.7):运算符(小数二进制、科学记数法、IEEE754标准)
       要讨论浮点数运算,牵涉到的知识比较多,下面一点一点的来逐步展开。为了便于同时讨论十进制和二进制数,我们做一个约定,我们把十进制数简写为N10,把二进制数简写为N2。
用户7801119
2020/09/27
8390
JavaScript的数据类型
该类型只有一个值undefined。对未声明和未初始化的变量执行typeof操作符都返回undefined
小小鱼儿小小林
2020/06/24
7650
C++003-C++变量和数据类型2
前两个数采用了科学记数法(scientific notation),第三个数保留了5位小数。浮点数用默认记数法defaultfloat编写:这种表示方法尽可能用多的位数,这个位数包括小数点前及小数点后的位数。 默认记数法特点
用户2225445
2023/10/16
3600
C++003-C++变量和数据类型2
0.1 + 0.2 不等于 0.3?原来是因为这个
浮点数精度丢失,一直是前端面试八股文里很常见的一个问题,今天我们就来深入的了解一下问题背后的原理,以及给一些日常处理的小技巧。
沐洒
2023/07/05
5890
0.1 + 0.2 不等于 0.3?原来是因为这个
前端最轻量级的精度计算工具库!
今天和同事聊起计算机中精度的话题。于是想起一个小巧的,快速的JavaScript库:big.js。它可用于任意精度的十进制算术运算。这里分享给大家
程序员老鱼
2023/12/11
1.5K0
前端最轻量级的精度计算工具库!
JavaScript数字运算必备库——big.js源码解析
在我们常见的JavaScript数字运算中,小数和大数都是会让我们比较头疼的两个数据类型。
黄Java
2020/12/01
4K0
js保留两位小数四舍五入_parsefloat保留两位小数
如果大家想对javascript有系统深入的学习,可以参阅 JavaScript启示录 PDF原书完整版 这本经典书籍
全栈程序员站长
2022/09/23
5.2K0
相关推荐
Js中Number对象
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验