凡是通过
- 逻辑运算符 (&&、 ||、 !)
- 运算符 (+、-、*、/)
- 关系操作符 (>、 <、 <= 、>=)
- 相等运算符 (==) 或者 if/while 条件的操作
如果遇到两个数据类型不一样的情况,都会出现隐式类型转换
==
的隐式类型转换规则
- 如果类型相同,无须进行类型转换。
- 如果其中一个操作值是
null
或者undefined
,那么另一个操作符必须为null
或者undefined
,才会返回true
,否则都返回false
。 - 如果其中一个是
Symbol
类型,那么返回false
。 - 两个操作值如果为
string
和number
类型,那么就会将字符串转换为number
; - 如果一个操作值是
boolean
,那么转换成number
。 - 如果一个操作值为
object
且另一方为string
、number
或者symbol
,就会把object
转为原始类型再进行判断(调用object
的valueOf/toString
方法进行转换)。
null == undefined // true 规则2
null == 0 // false 规则2
'' == null // false 规则2
'' == 0 // true 规则4 字符串转隐式转换成Number之后再对比
'123' == 123 // true 规则4 字符串转隐式转换成Number之后再对比
0 == false // true e规则 布尔型隐式转换成Number之后再对比
1 == true // true e规则 布尔型隐式转换成Number之后再对比
var a = {
value: 0,
valueOf: function() {
this.value++;
return this.value;
}
};
// 注意这里a又可以等于1、2、3
console.log(a == 1 && a == 2 && a ==3); //true f规则 Object隐式转换
// 注:但是执行过3遍之后,再重新执行a==3或之前的数字就是false,因为value已经加上去了,这里需要注意一下
===
不会出现类型类型转换, 但是也会有以下缺点:
===
运算符 (也包括==
运算符) 将数字-0
和+0
视为相等- 将
Number.NaN
与NaN
视为不相等.
+0 === -0
// true
NaN === NaN
// false
Object.is
与===
的区别如下:
===
运算符 (也包括==
运算符) 将数字-0
和+0
视为不相等- 将
Number.NaN
与NaN
视为相等.
Object.is(+0, -0)
// false
Object.is(NaN, NaN)
// true
Object.is
垫片函数如下
if (!Object.is) {
Object.is = function(x, y) {
// SameValue algorithm
if (x === y) { // Steps 1-5, 7-10
// Steps 6.b-6.e: +0 != -0
return x !== 0 || 1 / x === 1 / y;
} else {
// Step 6.a: NaN == NaN
return x !== x && y !== y;
}
};
}