1.其他类型转换成String
- Null和Undefiend:null 转换为 "null",undefined 转换为 "undefined"。
- Boolean:true 转换为 "true",false 转换为 "false"
- Number:直接转换
- Symbol:直接转换,但是只允许显式强制类型转换,使用隐式强制类型转换报错
显示转换:Number(value)、parseInt(value, radix)、parseFloat(value)、Boolean()、String()...
隐式转换:算术运算符,逻辑运算符,==运算符等
- Object:自动调用Object.prototype.toString()来返回内部属性[[Class]]的值,比如"[object Object]"
2. 其他类型转换成Number
- Undefined:转换为NaN
- Null:转换为0
- Boolean:true转换为1,false转换为0
- String:相当于使用Number()转换,如果包含非数字值转换为NaN,空字符串转换为0,只包含数字值转换为对应数字
- Symbol:不能转换,报错
- Object:会首先被转换为相应的基本类型值,如果返回的是非数字的基本类型值,则再遵循以上规则将其强制转换为数字。
那么问题来了,如何将Object转换为相应的基本类型值?
首先要介绍ToPrimitive方法,这是js中每个值隐含的自带的方法,用来将值 (无论是基本类型值还是对象)转换为基本类型值。如果值为基本类型,则直接返回值本身;如果值为对象,其看起来大概是这样:
/**
* @obj 需要转换的对象
* @type 期望的结果类型
*/
ToPrimitive(obj,type)
type的值为Number或者String,默认情况下,如果对象为Date对象,type为String;否则为Number:
(1) type为Number
- 调用obj的valueOf方法,如果结果为原始值,则返回,否则下一步
- 调用obj的toString方法,如果结果为原始值,则返回,否则下一步
- 抛出异常TypeError
(2) type为String
- 调用obj的toString方法,如果结果为原始值,则返回,否则下一步
- 调用obj的valueOf方法,如果结果为原始值,则返回,否则下一步
- 抛出异常TypeError
3. 其他值转换成Boolean
转换为false:
- undefined
- null
- false
- +0/-0
- NaN
- ''
其余均转换为为true
4. '=='隐式类型转换
如果两个值类型相同,进行===比较。
如果两个值类型不同,那么他们可能相等。根据下面规则进行类型转换,然后再比较。
(1)如果一个是null、一个是undefined,那么相等。
(2)如果一个是字符串,一个是数值,把字符串转换成数值再进行比较。
(3)如果任一值是true,把它转换成 1 再比较;如果任一值是false,把它转换成 0 再比较。
(4)如果一个是对象,另一个是数值或字符串,把对象转换成基础类型的值再比较。对象转换成基础类型,利用它的toString或者valueOf方法。
(5)任何其他组合,都不相等。
总之,尽可能把操作符两边的值转换成Number去比较
例如:
"1" == true:类型不等,true 会先转换成数值 1 ,现在变成 “1” == 1 ,再把 “1” 转换成 1 ,比较 1 == 1 ,相等。
要注意这个问题:
5. '+'隐式类型转换
操作符的两边有至少一个string类型变量时,两边的变量都会被隐式转换为字符串;
其他情况下两边的变量都会被转换为数字
1 + '23' // '123'
1 + false // 1
1 + Symbol() // Uncaught TypeError: Cannot convert a Symbol value to a number
'1' + false // '1false'
false + true // 1
[1,2] + [1,2] // '1,21,2'
{name:'Jack'} + {age: 18} // NaN
({name:'Jack'}) + ({age: 18}) // "[object Object][object Object]"
这里注意一下'+'单目运算符可以将字符串转换为数字,比如+'1' -> 1,但是如果是+'abc'那就是输出NaN了
6. '-''*''/'隐式类型转换
往Number转换,主要是注意会得出NaN
1 * '23' // 23
1 * false // 0
1 / 'aa' // NaN
7.'>''<'隐式类型转换
都是字符串,比较字母表顺序
'ca' < 'bd' // false
'a' < 'b' // true
其他情况下,转换成Number比较
'12' < 13 // true
false > -1 // true
注意对象的转换过程
var a = {}
a > 2 // false
a.valueOf() // {}, 上面提到过,除Date外对象ToPrimitive默认type为number,所以先valueOf,结果还是个对象,下一步
a.toString() // "[object Object]",现在是一个字符串了
Number(a.toString()) // NaN,根据上面 < 和 > 操作符的规则,要转换成数字
NaN > 2 //false,得出比较结果