一篇文章搞定JavaScript类型转换(面试常见)


Posted in Javascript onJanuary 21, 2017

为啥要说这个东西?一道面试题就给我去说它的动机。

题如下:

var bool = new Boolean(false);
if (bool) {
 alert('true');
} else {
 alert('false');
}

运行结果是true!!!

其实啥类型转换啊,操作符优先级啊,这些东西都是最最基本的。犀牛书上有详细的介绍。但我很少去翻犀牛书的前5章。。。

比如说优先级那块儿,很多书都教育我们,“不用去背诵优先级顺序,不确定的话,加括号就行了。“平常我们写代码时也确实这么做的。

但现实是啥呢?面试时会出这种题,让你来做。。。真不知道这种题的意义是啥。。。

抱怨到此为止,本文尝试来解决类型转换问题,争取把《JS权威指南》49页那个表背下来。

都有哪些东西是假值?

共6个:

0或+0、-0,NaN
""
false
undefined
null

上面的顺序是按照基本类型来排列的。

除此之外的一律不是!!哪怕是如下形式:

Infinity
'0'、'false'、" "(空格字符)
任何引用类型:[],{},function(){}

if (a && b)的正确理解方式是:a && b进行表达式求值后,然后再转换为Boolean类型。

&&是种短路语法,求值后不一定是个Boolean类型,更不是两边转化布尔值再运算。

比如 2&&3 的结果是3,不是true。

所以if(a && b),我们平常理解的那种,"如果a和b同时为真的话",是一种错误的描述方式。

其他基本类型转化为字符串,基本和预期的一样:

console.log("" + null);   // "null"
console.log("" + undefined); // "undefined"
console.log("" + false);   // "false"
console.log("" + true);   // "true"
console.log("" + 0);     // "0"
console.log("" + NaN);    // "NaN"
console.log("" + Infinity); // "Infinity"

其他基本类型转化为数字,需要特殊记忆:

console.log(+null);     // 0
console.log(+undefined);   // NaN
console.log(+false);     // 0
console.log(+true);     // 1
console.log(+"");      // 0
console.log(+'1');      // 1
console.log(+'1x');     // NaN

其中null,空字符是0,undefined是NaN。

以上,基本类型转换都说明白了。

下面来看看引用类型转换为基本类型。

引用类型转换为布尔,始终为true

引用类型转换为字符串

1.优先调用toString方法(如果有),看其返回结果是否是原始类型,如果是,转化为字符串,返回。

2.否则,调用valueOf方法(如果有),看其返回结果是否是原始类型,如果是,转化为字符串,返回。

3.其他报错。

引用类型转化为数字

1.优先调用valueOf方法(如果有),看其返回结果是否是基本类型,如果是,转化为数字,返回。

2.否则,调用toString方法(如果有),看其返回结果是否是基本类型,如果是,转化为数字,返回。

3.其他报错。

首先我们看看常见引用类型toString和valueOf返回什么?

var a = {};
console.dir(a.toString());  // "[object Object]"
console.dir(a.valueOf());  // 对象本身
var b = [1, 2, 3];
console.dir(b.toString());  // "1,2,3"
console.dir(b.valueOf());  // 对象本身
var c = [[1],[2]];
console.dir(c.toString());  // "1,2"
console.dir(c.valueOf());  // 对象本身
var d = function() {return 2};
console.dir(d.toString());  // "function() {return 2}"
console.dir(d.valueOf());  // 对象本身

因此对应的转换为字符串和数字的情形是:

var a = {};
console.dir(a + "");     // "[object Object]"
console.dir(+a);       // NaN
var b = [1, 2, 3];
console.dir(b + "");     // "1,2,3"
console.dir(+b);       // NaN
var c = [[1],[2]];
console.dir(c + "");     // "1,2"
console.dir(+c);       // NaN
var d = function() {return 2};
console.dir(d + "");     // "function () {return 2}"
console.dir(+d);       // NaN

再来个报错的情形:

var a = {};
a.toString = function() {return {};}
console.log("" + a);     // 报错
console.log(+a)       // 报错

以上类型转换规律基本说完。

最后来说一下万恶的“==”

面试题如下:

var a = false;
var b = undefined;
if (a == b) {
 alert('true');
} else {
 alert('false');
}

本以为会弹出true的。天那!为啥是false?

哈哈。。。

双等号,如果两边类型不同,会有隐式转换发生。犀牛书75页总结如下:

1,null和undefined,相等。

2,数字和字符串,转化为数字再比较。

3,如果有true或false,转换为1或0,再比较。

4,如果有引用类型,优先调用valueOf。

5,其余都不相等。

因此有:

console.log(undefined == false); // false
console.log(null == false);   // false
console.log(0 == false);     // true
console.log(NaN == false);    // false
console.log("" == false);    // true

0 == false之所以为true根据第3条。

"" == false之所以为true根据第3条,变成了"" == 0,再根据第2条。

第4条再来一个例子:

console.log([[2]] == '2')

其上结果为true,原因如下:

[[2]]的valueOf是对象本身,不是基本类型。

尝试调用toString的结果是'2'。

因此变成了'2'和数字2的比较。根据第2条,相等。WTF!!

最后说句,使用"==="就没有这些问题了。

以上所述是小编给大家介绍的一篇文章搞定JavaScript类型转换(面试常见),希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
用javascript动态调整iframe高度的方法
Mar 06 Javascript
javascript 词法作用域和闭包分析说明
Aug 12 Javascript
jQuery 1.5 源码解读 面向中高阶JSER
Apr 05 Javascript
动态标签 悬停效果 延迟加载示例代码
Nov 21 Javascript
快速解决jquery之get缓存问题的最简单方法介绍
Dec 19 Javascript
简介JavaScript中POSITIVE_INFINITY值的使用
Jun 05 Javascript
javascript简单实现类似QQ头像弹出效果的方法
Aug 03 Javascript
jQuery Select下拉框操作小结(推荐)
Jul 22 Javascript
JS简单实现数组去重的方法示例
Mar 27 Javascript
使用JS在浏览器中判断当前网络连接状态的几种方法
May 05 Javascript
vue项目如何刷新当前页面的方法
May 18 Javascript
vue使用axios上传文件(FormData)的方法
Apr 14 Javascript
超全面的JavaScript开发规范(推荐)
Jan 21 #Javascript
Mongoose学习全面理解(推荐)
Jan 21 #Javascript
ng-options和ng-checked在表单中的高级运用(推荐)
Jan 21 #Javascript
vue实现添加标签demo示例代码
Jan 21 #Javascript
微信小程序 数据交互与渲染实例详解
Jan 21 #Javascript
前端编码规范(3)JavaScript 开发规范
Jan 21 #Javascript
Bootstrap框架安装使用详解
Jan 21 #Javascript
You might like
PHP中echo,print_r与var_dump区别分析
2014/09/29 PHP
PHP采用curl模仿用户登陆新浪微博发微博的方法
2014/11/07 PHP
PHP的反射机制实例详解
2017/03/29 PHP
thinkPHP5项目中实现QQ第三方登录功能
2017/10/20 PHP
Aster vs KG BO3 第三场2.19
2021/03/10 DOTA
jQuery 行背景颜色的交替显示(隔行变色)实现代码
2009/12/13 Javascript
Javascript继承(上)——对象构建介绍
2012/11/08 Javascript
使用JavaScript构建JSON格式字符串实现步骤
2013/03/22 Javascript
jQuery+ajax中getJSON() 用法实例
2014/12/22 Javascript
js获取数组的最后一个元素
2015/04/14 Javascript
JavaScript汉诺塔问题解决方法
2015/04/21 Javascript
JSON相关知识汇总
2015/07/03 Javascript
jQuery实现自动切换播放的经典滑动门效果
2015/09/12 Javascript
jQuery配合coin-slider插件制作幻灯片效果的流程解析
2016/05/13 Javascript
JS中判断字符串中出现次数最多的字符及出现的次数的简单实例
2016/06/03 Javascript
基于MVC5和Bootstrap的jQuery TreeView树形控件(二)之数据支持json字符串、list集合
2016/08/11 Javascript
Vue.js 2.0 和 React、Augular等其他前端框架大比拼
2016/10/08 Javascript
vuejs 单文件组件.vue 文件的使用
2017/07/28 Javascript
jQuery plugin animsition使用小结
2017/09/14 jQuery
Puppeteer环境搭建的详细步骤
2018/09/21 Javascript
使用typescript改造koa开发框架的实现
2020/02/04 Javascript
Node.js中的异步生成器与异步迭代详解
2021/01/31 Javascript
Python使用email模块对邮件进行编码和解码的实例教程
2016/07/01 Python
Python基于matplotlib实现绘制三维图形功能示例
2018/01/18 Python
python实现二维插值的三维显示
2018/12/17 Python
Python 占位符的使用方法详解
2019/07/10 Python
Python获取一个用户名的组ID过程解析
2019/09/03 Python
Python 脚本拉取 Docker 镜像问题
2019/11/10 Python
pytorch模型预测结果与ndarray互转方式
2020/01/15 Python
快速解决jupyter启动卡死的问题
2020/04/10 Python
2014年酒店前台工作总结
2014/11/14 职场文书
拾金不昧感谢信范文
2015/01/21 职场文书
2016庆祝国庆67周年宣传语
2015/11/25 职场文书
读《教育心理学》心得体会
2016/01/22 职场文书
《神奇的鸟岛》教学反思
2016/02/22 职场文书
spring boot项目application.properties文件存放及使用介绍
2021/06/30 Java/Android