开头

js数字没有明确区分浮点数和整数类型,统一用number类型表示。

number 基于IEEE 754标准实现 js采用的是双精度(64位二进制)

我们看一个基于IEEE 754标准实现都有会有的经典问题

0.1 + 0.2 === 0.3 //false
// 原因是 0.1 0.2 不精确,相加不等于0.3 而是一个类似0.30000000004 的值,所以条件判断结果为false

我们很容易修正这个错误,知道是因为偏差值出现问题,我们可以定义一个偏差值,在此偏差值内我们认为两者相等。对于js来说,2^-52比较合适。目前ES6为我们提供了这个偏差值

// Number.EPSILON ES6提供的比较偏差值
// polyfill
if(!Number.EPSILON){
Number.EPSILON = Math.pow(2, -52)
} //判断相等的方式
function numbersCloseEnoughToEqual(n1,n2) {
return Math.abs( n1 - n2 ) < Number.EPSILON;
}
var a = 0.1 + 0.2;
var b = 0.3;
numbersCloseEnoughToEqual( a, b ); // true
numbersCloseEnoughToEqual( 0.0000001, 0.0000002 ); // false
特殊值

比起其他语言,js提供了数字的很多特殊值,我们看一下它们出现的场合以及判别方式

1.NaN

不是数字的数字,表示数字运算和数字解析中的错误

,比如数字运算中操作数不为数字,或者值无法被解析为十进制或十六进制,看下面的例子

var a = 2 / "foo" //NaN
var b = parseInt("f") //NaN

判别

尝试一 、=

// 意料之外 NaN和自身不相等
NaN == NaN
NaN === NaN

尝试二 isNaN

// 全局isNaN函数
var a = 2 / "foo"
is NaN(a) // true [ undefined, null, true, false, {}, "1" , "foo" ].forEach( e => {
console.log(e, isNaN(e))
})
// 结果 对于undefined、{} 、"foo"都返回了true,明显他们不是NaN
undefined true
null false
true false
false false
{} true
1 false
foo true //我们需要加一层保险,目前这个方案已经被ES6实现为Number.isNaN //polyfill
if(!Number.isNaN) {
Number.isNaN = function(n) {
return typeof n === "number" && isNaN(n)
//或者
return n!==n
}
}

2.无穷数 传统编译语言中 除以0 会抛出编译错误或者运行时错误,例如除以0,在js中,这个错误被定义为常量,无穷数 Infinity(Number.POSITIVE_INFINITY),还有在运算中结果溢出的情况也会出现Infinity

var a = 1 / 0; // Infinity(Number.POSITIVE_INFINITY)

var b = -1 / 0; // -Infinity(Number.NEGATIVE_INfiNITY)

var a = Number.MAX_VALUE; // 1.7976931348623157e+308
a + a; // Infinity
a + Math.pow( 2, 970 ); // Infinity // 无穷除以无穷
Infinity / -Infinity //NaN // 有穷正数除以Infinity
1 / Infinity // 0 // 有穷负数除以Infinity
-1 / Infinity // -0

3.零值(0、-0) -0 是一些数学运算中会出现

var a = 0 / -3; // -0
var b = 0 * -3; // -0

-0的转换

a.toString(); // "0"
a + ""; // "0"
String( a ); // "0"
// JSON也如此,很奇怪
JSON.stringify( a ); // "0"而不是"-0" +"-0"; // -0
Number( "-0" ); // -0
JSON.parse( "-0" ); // -0 // 比较操作
var a = 0;
var b = 0 / -3; a == b; // true
-0 == 0; // true
a === b; // true
-0 === 0; // true
0 > -0; // false
a > b; // false

区分0和-0

function isNegZero(n) {
n = Number(n)
return (n === 0) && (1 / n === -Infinity)
}
// 案例
isNegZero( -0 ); // true
isNegZero( 0 / -3 ); // true
isNegZero( 0 ); // false

对于特殊等式的统一处理(能够处理 NaN -0) Object.is()

var a = 2 / "foo";
var b = -3 * 0; Object.is( a, NaN ); // true
Object.is( b, -0 ); // true
Object.is( b, 0 ); // false //一个简单的polyfill
if (!Object.is) {
Object.is = function(v1, v2) {
// 判断是否是-0
if (v1 === 0 && v2 === 0) {
return 1 / v1 === 1 / v2;
}
// 判断是否是NaN
if (v1 !== v1) {
return v2 !== v2;
}
// 其他情况
return v1 === v2;
};
}

深入js系列-类型(数字)的更多相关文章

  1. 深入js系列-类型(隐式强制转换)

    隐式强制转换 在其可控的情况下,减少冗余,让代码更简洁,很多地方都进行了隐式转换,比如常见的三目表达式.if().for().while.逻辑运算符 || &&,适当通过语言机制,抽象 ...

  2. 【转载】JS Number类型数字位数及IEEE754标准

    JS的基础类型Number,遵循 IEEE 754 规范,采用双精度存储(double precision),占用 64 bit.如图 意义 1位用来表示符号位 11位用来表示指数 52位表示尾数 浮 ...

  3. JS Number类型数字位数及IEEE754标准

    JS的基础类型Number,遵循 IEEE 754 规范,采用双精度存储(double precision),占用 64 bit.如图 意义 1位用来表示符号位 11位用来表示指数 52位表示尾数 浮 ...

  4. 深入js系列-类型(显式强制转换)

    什么是显式 这里的显式和隐式是以普遍的标准来进行讨论的,你能看出来是怎么回事,那么它对你是"显式",相反你不知道的话,对你就是"隐式" 抽象操作 字符串.数字. ...

  5. 深入js系列-类型(对象)

    开篇 值的传递方式 1.值传递 表示传递过程中复制了值 2.引用传递 表示传递过程中传递的是值的引用 js的传递方式 值传递 看下面的例子 // 这里值传递很容易理解 var a = 1 var b ...

  6. 深入js系列-类型(null)

    首先null是表示什么状态呢 这个是需要和上篇的undefined做一个区分 undefined 从未赋值 非关键词(也就是可以定义为变量名或者赋值给它) null 曾经赋值.目前没值 关键词 typ ...

  7. 深入js系列-类型(开篇)

    思考 作为一个编程人员,你可能从来没仔细思考过,为什么这么多高级语言会有类型这东西. 实际上,类型有点类似生活中的类别,我们日常生活,早已经把这个概念理解到了,切肉和切水果会用不同的刀. 语言级别的类 ...

  8. js中的数字格式变成货币类型的格式

    <!DOCTYPE HTML> <html lang="en-US"> <head> <meta charset="UTF-8& ...

  9. 【D3.V3.js系列教程】--(十二)坐标尺度

    [D3.V3.js系列教程]--(十二)坐标尺度 1.多种类型的缩放尺度 Quantitative Scales Linear Scales Identity Scales Power Scales ...

随机推荐

  1. 初识Go语言--(2)Hello World

    新建hello.go文件,内容如下 package main import "fmt" func main() { //输出Hello World fmt.Println(&quo ...

  2. Excel技能提升

    函数 字符串全半角之间的转换 ASC将全角英文字母转换为半角英文字母,其语法是ASC(text) WIDECHAR()将半角英文字母转换为全角英文字母,语法是=WIDECHAR(text) find( ...

  3. MP3文件信息修改

    MP3文件信息 参考链接:https://www.jianshu.com/p/e368517ec7b9 总结: ID3V1在MP3文件后面;ID3V2在MP3文件前面;现在有些文件是V1的,有些文件是 ...

  4. NET 在一个数组中查找另一个数组所在起始位置(下标从0开始,未找到返回-1)

    问题: 如果 search 在 dist 中顺序出现而不要求连续出现,那代码应该如何修改?如何计算这种匹配的可能性? 数组 search=[5,4,6],在数据 dist=[1,5,5,4,3,4,5 ...

  5. 初识Markdown

    目录 一.基础语法 二.语法规则 1.标题 2.列表 3.文字格式 4.链接 5.图片 6.引用 7.水平分隔线 8.代码块 9.表格 10.文档目录 11.转义定义 写在前面 Markdown(简称 ...

  6. 【翻译】Tusdotnet中文文档(3)自定义功能和相关技术

    自定义功能和相关技术 本篇按照如下结构翻译 自定义功能 自定义数据仓库 相关技术 架构和总体概念 自定义数据仓库 tusdotnet附带一个存储库TusDiskStore,它将文件保存在磁盘上的一个目 ...

  7. PIE SDK内存矢量数据的创建

    1.功能简介 GIS将地理空间数据表示为矢量数据和栅格数据.矢量数据模型使用点.线和多边形来表示具有清晰空间位置和边界的空间要素,如控制点.河流和宗地等,每个要素被赋予一个ID,以便与其属性相关联.栅 ...

  8. elasticsearch原理学习

    用es也差不多一年左右了,但是都是只会用,底层做了什么一窍不通,没有核心竞争力,循序渐进,一个一个攻破,理解的多了,读的多了,自然能力就上去了,es底层是基于lucene的,所以今天先从lucene下 ...

  9. Angular4项目运行时URL自动加#方法

    import {HashLocationStrategy , LocationStrategy} from '@angular/common'; @NgModule({   declarations: ...

  10. 安装php源码包内的扩展

    本地环境 PHP 7.0.4 (cli) (built: Mar 13 2016 21:50:22) ( NTS ) 安装 进入源码包中的ext文件夹中 [root@test etc]# cd /us ...