-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
JS-类型&类型判断 #97
Comments
String一、String1.1 字符串
|
Number一、语法1.1 概述
1.2
|
undefined一、概述ECMAScript中Undefined(首字母大写)类型定义是:有且只有一个undefined(首字母小写)值的类型。任何没有赋值的变量的值都是undefined。 var a;
console.log(a); // undefined 但Undefined类型只存在于规范中,实际实现中并没有定义Undefined类型。
二、void 0替代undefinedvoid运算符返回的是undefined。
代码中常常看到使用void 0替代undefined(打包工具也会自动转换),这是为啥呢?:
2.1 void 0 更安全如上文,undefined值可以作为变量的,万一值被重新了,那岂不是凌乱了。 2.2 void 0 体积小好多代码压缩工具都会把undefined替换成void 0。字符串“void 0” 比“undefined”更短一些(额,少了3个字符)。 参考 |
练习1. 输出以下代码的执行结果并解释为什么var a = {n: 1};
var b = a;
a.x = a = {n: 2};
console.log(a.x)
console.log(b.x) |
typeof 内部根据变量的类型标签(type tag)获取类型信息的。JS是动态类型的变量。每个变量在存储时除了存储变量值还需要存储变量的类型。JS里使用32位(bit)存储变量信息。低位的1~3个bit存储变量类型信息:
如何标记
|
|
深入浅出JS类型判断JS中判断数据类型的方式有很多
一、回顾JS数据类型分为基本类型和引用类型。
引用类型
函数是一种特殊的对象,即可调用的对象。 二、typeof2.1 语法
console.log(typeof null) // object
console.log(typeof undefined) // undefined
console.log(typeof 1) // number
console.log(typeof 1.2) // number
console.log(typeof "hello") // string
console.log(typeof true) // boolean
console.log(typeof Symbol()) // symbol
console.log(typeof (() => {})) // function
console.log(typeof {}) // object
console.log(typeof []) // object
console.log(typeof /abc/) // object
console.log(typeof new Date()) // object
2.2 原理JS是动态类型的变量,每个变量在存储时除了存储变量值外,还需要存储变量的类型。JS里使用32位(bit)存储变量信息。低位的1~3个bit存储变量类型信息,叫做类型标签(type tag) .... XXXX X000 // object
.... XXXX XXX1 // int~~~~
.... XXXX X010 // double
.... XXXX X100 // string
.... XXXX X110 // boolean
如何识别
|
一、类型种类
基于
typeof
返回值进行分类:虽然
typeof null === 'object'
,但也作为一个类型ES6新增类型
其中:
值类型和引用类型区别
字符串变量虽然长度不一,但是具体的某个字符串的大小是固定的。
二、类型转化
2.1 装箱和拆箱
基本类型(除了null, undefined)都有对应引用类型对象。并且会根据使用场景会自动地把基本类型转成对象(装箱),或者把对象转成基本类型(拆箱)。
2.1.1 装箱
显示装箱
除了调用基本类型对应的引用类型构造函数外,可以利用
Object
方法进行装箱。PS:可以利用
Object(null)
判断参数是否为非null的对象。2.1.2 拆箱
当需要基本类型时,对象也会自动转成基本类型(拆箱)
1. 转number(比如算术运算符中的对象,需要转成number)
valueOf
方法并且该方法返回原始值,则调用该方法,并转成number;内置对象中只有
Boolean
,String
,Number
,Date
重写了valueOf
方法,其他大部分都还是默认的valueOf行为。toString
方法并且该方法返回原始值,则调用该方法,并转成number;2. 转string比如
+
运算中的对象(比如模板字符串中)toString
方法并且该方法返回原始值,则调用该方法,并转成string;valueOf
方法并且该方法返回原始值,则调用该方法,并转成string;注意:转number和转string的过程正好相反。
3. 转boolean(比如逻辑运算中)
true
。即使是
new Boolean(false)
对象new Boolean(false)
和Boolean(false)
返回值是不一样的,前者是对象,后者是基本值。4. Demo
2.2 参与运算的类型转换
运算符对表达式的类型有要求,不满足要求的会进行隐式的类型转换。但有些运算符可能支持多种类型的数据,这里就涉及一些优先类型转换规则:
+
(string和number都可以)当其中一个是字符串时,会把另一个原始值(拆箱之后)转成字符串。
>
,>=
,<=
,<
)(string
和number
都可以)都是
string
时才进行字符串比较,其他转number
进行比较==
,!=
)(基本类型和引用类型都可以)===
);null
和undefined
值不会发生类型转换,即效果同===
,但是特例null == undefined
为true;null
和undefined
没有封装类型,也没有方法(不存在valueOf
,toString
方法)==
比较;null
,undefiend
)都转成Number进行比较,即String和bool不会互转,都会统一转成Number。2.2.2 特例
+'' === 0
;注意
+[] === 0
,因为空数组的toString
返回是空字符串。2.2.3 总结下:
+
中字符串优先级高些,其他基本上都是转number;2.3 显示类型转换
2.3.1 使用构造函数
Boolean, Number, String, Object
可以显示的转成指定的引用类型。Number/Boolean/String
的函数调用和new方式调用返回值不一样;null
和undefined
不存在对应的对象,Object(null)
和Object(undefined)
返回空对象{}
。2.3.2 一元运算符显示转化
!
运算符不涉及拆包过程(所有对象都是true)。2.3.3 内置方法
parseInt(string[, radix])
实参
null
,undefined
,0
是无效值,就当做没有传值。非int值会转成Int。
parseInt
是逐个字符解析实参string
的,遇到非法字符或者字符串结尾,就把已经解析的结果返回,如果第一个字符无法解析则返回NaN
。parseFloat(string)
三、类型判断
1.
typeof
虽然简单方便,但不能区分null和object以及各种常用内置对象;但是如果只是识别函数,也可以使用
typeof
(常见于第三方库/util中)。原理:???
2. 更常规的用法调用
Object.prototype.toString
方法。underescorejs 源码片段:
原理:
toString
格式字符串(转字符串标签)。这里的
type
应该是指对象默认描述字符串。toString
方式更多的是判断各种对象类型,所以对于基本类型会有装箱的操作(除了null, undefined)。从ES5开始null, undefined也可以调用了缺点:
Symbol.toStringTag
修改默认的toString
字符串;NaN
,Infinity
3. 区分
NaN
,Infinity
值NaN
,Infinity
都是number值(它俩类型一样),使用方法2是不能区分的。还好Number有相关静态方法
isNaN
,isInfinity
(宿主也有同名的全局方法)。4.
Array.isArray
instanceof
都存在这个问题,为啥单独给只提供个Array.isArray
?其他方式或多或少有点问题,
Array.isArray
更靠谱些。四、参考
The text was updated successfully, but these errors were encountered: