原始值转原始值

转字符串

  1. String(undefined); // -> 'undefined'
  2. String(null); // -> 'null'
  3. String(3); // -> '3'
  4. String(true); // -> 'true'
  5. String(false); // -> 'false'

转数字

Number()方法转换数字时,如果出现非数字的字符时会直接返回NaN(null 、布尔值除外),且可以识别浮点数。
parseInt()方法,首先是可以将数字或者字符串转换成为一个整数数字,如果字符串的第一个字符不能被转换为数字,直接返回NaN;字符串中出现不能转为数字的字符,该方法会进行截取操作。方法还有第二个参数(可选),表示要解析数字的基数,介于2~36之间。(该篇主要讨论数据类型的转换,所以在此不做过多介绍。)

  1. Number(undefined); // -> NaN
  2. Number(null); // -> 0
  3. Number('3'); // -> 3
  4. Number('.3'); // -> 0.3
  5. Number('1 3'); // -> NaN
  6. Number('3a'); // -> NaN
  7. Number('a3'); // -> NaN
  8. Number(true); // -> 1
  9. Number(false); // -> 0
  10. Number(''); // -> 0
  11. parseInt(undefined); // -> NaN
  12. parseInt(null); // -> NaN
  13. parseInt('3'); // -> 3
  14. parseInt('.3'); // -> NaN
  15. parseInt('0.3'); // -> 0
  16. parseInt('3 1'); // -> 3
  17. parseInt('3a'); // -> 3
  18. parseInt('a3'); // -> NaN
  19. parseInt(true); // -> NaN
  20. parseInt(false); // -> NaN

转布尔值

这里就涉及到一个虚值(falsey)的概念
虚值:undefined、null、0、false、NaN、’’。(注意''' '可不一样,空格属于一个字符)
只要是虚值转换布尔值都为false,反之都为true。

  1. Boolean(' '); // -> true
  2. Boolean(''); // -> false
  3. Boolean(undefined); // -> false
  4. Boolean(null); // -> false
  5. Boolean(0); // -> false
  6. Boolean(false); // -> false
  7. Boolean(NaN); // -> false

引用类性值转原始值

引用类性值转数字

  1. 首先通过valueOf()方法,看其返回值是否是原始值。
  2. 如果为原始值,直接通过Number()方法转换为数字。
  3. 如果是非原始值,则调用其对应类型的toString()方法(基于原型链查找)。
  4. 如果返回的值是原始值,直接通过Number()方法转换为数字。
  5. 如果通过重写toString()更改了返回值,返回的是一个对象的话,直接报错。

    注意:valueOf()方法,如果没有被我们重写的话,默认返回的就是自身。

    1. Number({});
    2. // {}.valueOf() -> {} -> {}.toStirng() -> '[object Object]'
    3. // -> Number('[object Object]') -> NaN
    4. Number([]);
    5. // [].valueOf() -> [] -> [].toStirng() -> '' -> Number('') -> 0
    6. Number(function () {});
    7. // (function () {}).valueOf() -> (function () {}).toString() -> 'function () {}' -> Number('function () {}') -> NaN

    引用类性值转字符串

  6. 先通过toString()方法, 看其返回值是否是原始值。

  7. 如果是原始值,调用其包装类所对应的toString()方法。
  8. 如果是重写的toString()返回的是引用类型值,则调用valueOf()方法。
  9. 如果返回原始值,调用其包装类所对应的toString()方法。
  10. 如果还是引用类型值,直接报错。 ```javascript // 这种两种转换方式是等效的 String([]) === ‘’ + [];

String(undefined); // -> ‘undefined’ String(null); // -> ‘null’

var obj = { toString () { return []; }, valueOf () { return {}; } } String(obj); // 报错 Uncaught TypeError: Cannot convert object to primitive value at String

var obj1 = { toString () { return []; }, valueOf () { return 3; } } String(obj1); // -> ‘3’

var obj2 = { toString () { return true; }, valueOf () { return 3; } } String(obj2); // -> ‘true’

  1. <a name="wrpUg"></a>
  2. ## 双等隐式转换规则
  3. 引用类型值和原始类型值进行比较时,都通过`Number()`方法转为数字后进行比较。<br />两个引用类性值比较时,会根据指针(栈内存中的引用地址)进行对比。<br />特例:<br />`undefined == null // -> true`,undefined 和 null 除了彼此相等和自己相等之外,与其他任何类型的值都不相等。<br />`NaN == NaN // -> false`,NaN 与任何值都不相等包含自己本身。
  4. ```javascript
  5. undefined == null // -> true
  6. NaN == NaN // -> false
  7. // question
  8. console.log([] == ![]);
  9. console.log({} == !{});
  10. /**
  11. * "!" 逻辑运算符 优先级 17
  12. * !expr 若 expr 可转换为 true, 则返回 false;否则, 返回 true
  13. * "==" 比较运算符 优先级 11
  14. * 相等比较操作符会为两个不同类型的操作数转换类型
  15. */
  16. /**
  17. * [] == ![]
  18. * 先运算 ![] []不是一个虚值, 转布尔值就为true, !true -> false;
  19. * [] == false
  20. * [] -> [].valueOf() -> [] -> [].toString() -> '' -> Number('') -> 0
  21. * false -> Number(false) -> 0
  22. * 0 == 0 -> true
  23. */
  24. /**
  25. * {} == !{}
  26. * 先运算 !{} {}不是一个虚值, 转布尔值就为true, !true -> false;
  27. * {} == false
  28. * {} -> {}.valueOf() -> {} -> {}.toString() -> '[object Object]' -> Number('[object Object]') -> NaN
  29. * false -> Number(false) -> 0
  30. * 0 == NaN -> false
  31. */