# JavaScript 类型

# 类型

基本类型

string number boolean null undefined symbol Bigint

引用类型

对象 函数

# 类型转换

JS隐式类型转换发生在我们使用 + - * / == < > 这些运算符时,这些运算符只能操作基本数据类型,对于对象类型需要先调ToPrimitive算法转换成基本类型

# 基本类型值的隐式类型转换

+ 操作符两边至少有一个值是string类型时,都转为string;否则都转为number

// 都转为string 1 -> "1"
console.log(1 + "23"); // "123"

// 都转为number,false -> 0
console.log(1 + false); // 1

// 都转为string,false -> "false"
console.log("1" + false); // "1false"

// 都转为number,true -> 1,false -> 0
console.log(true + false); // 1

- * / 操作符两边都转为number

console.log(25 - "23"); // 2
console.log(1 * false); // 0
// Number("a")为NaN
console.log(1 / "a"); // NaN

== 操作符两边都转为number

// true -> 0
console.log(2 == true); // false
// "0" -> 0, false -> 0
console.log("0" == false); // true
// "0" -> 0
console.log("0" == 0) ; // true

对于 > <,全是字母比较按字母顺序,其余的都转换成number在比较

// 按字母顺序g比f大
console.log("g" > "f"); // true
// 按字母顺序f比g小
console.log("fh" > "ga"); // false
// 转换成number,"12" -> 12
console.log("12" < 13); // true
// 转换成number,false -> 0
console.log(false < -1); // false
// 转换成number,"a" -> NaN, NaN做比较都是false
console.log("a" < 9999); // false

请问

console.log(undefined + 10); // NaN
// 转换为number类型,undefined -> NaN

console.log(undefined + "10");
// 转换为string类型,undefined -> "undefined10"

# 引用类型值的隐式类型转换

ToPrimitive算法

ToPrimitive,是JS中每个值隐含的自带的方法,他可以将任何类型的值转换为基本类型的值。这是一个内部算法,是JS在内部执行时遵循的一套规则。

既然这些运算符只能操作基本数据类型,那必然有能将引用类型转换成基本类型机制,这个机制就是ToPrimitive算法。通过此算法将值转换成基本类型后,再进行上节中的基本类型值的比较。

调用ToPrimitive函数时,会被传递一个字符串参数 hint,表示要转换到的原始值的预期类型。 hint 参数的取值是 "number"、"string" 和 "default" 中的任意一个

当hint为number或default时:

  1. 调用Object的valueOf方法,如果为原始值,则直接返回;否则进行下一步;
  2. 调用Object的toString方法,如果为原始值,则直接返回;否则进行下一步;
  3. 抛出TypeError异常;

当hint为string时:

  1. 调用Object的toString方法,如果为原始值,则直接返回;否则进行下一步;
  2. 调用Object的valueOf方法,如果为原始值,则直接返回;否则进行下一步;
  3. 抛出TypeError异常;

那么hint参数是依据什么规则确定的呢? 有如下几点:

  1. 一般情况下,+ 连接运算符传入的参数是default;
  2. 当是 - * / > < == 操作符时,hint为number;
  3. 对于 String(str) 和模版字符串 ${str} 等情况,传入的参数是string
console.log(2 > {}); // false

/**
 * 1. {}不是基本数据类型,所以调用ToPrimitive
 * 2. hint为number,首先调用valueOf方法,返回{}
 * 3. {}还不是基本数据类型,调用toString()方法,返回"[object Object]"
 * 4. "[object Object]"是基本类型,结束ToPrimitive
 * 5. 比较2 > "[object Object]",需要都转换为number类型
 * 6. Number("[object Object]")为NaN
 * 7. 比较2 > NaN,返回false,结束
 */

# toString与valueOf

  • toString():它的作用是返回一个反映这个对象的字符串;
  • valueOf():它的作用是返回它相应的原始值;

上面说到调用ToPrimitive方法后,会根据hint情况调用toString和valueOf方法来返回最终值,那么toString和valueOf是根据什么规则转化的呢?

下表展示了各种数据类型调用toString和valueOf方法后的输出值:

js-004

陕ICP备20004732号-3