强制类型转换

将值从一种类型转换为另一种类型通常称为类型转换,这是显式的情况。隐式的情况被称为强制类型转换

在书中,作者还提出一种区分方式:

类型转换发生在静态类型语言的编译阶段,强制类型转换发生在动态类型语言的运行时。

JS天生的动态类型语言,所以JS中统一讲强制类型转换。


一、JS中的强制类型转换

首先看如下所示代码:

var a = 42;
var b = a + ''; // 隐式强制类型转换
var c = String(a); // 显式强制类型转换

相较于,第三行代码使用String对变量a进行封装而言,第二行代码的类型转换并非那么明显,更像是'+'操作符的副作用,所以我们把这种情况称为隐式强制类型转换,而显式的通过原生函数封装的方式则称为显式强制类型转换。当然,这只是作者的一种观点而已,但是这种观点对于区分这两种类型转换还是有好处的。


二、JSON.stringify()

如果要将对象字符串化,可以使用JSON.stringify()。这个方法可以带参数,参数可以是以下两种情况:

  1. 参数是一个字符串数组,数组元素是要执行序列化的对象的属性名称:
var a = {
b: 1,
c: '1',
d: [1,2,3]
}; JSON.stringify(a, ['b', 'c']); // "{"b":1,"c":"1"}"
  1. 参数是一个函数,这个函数有两个参数,key和value,这个函数会首先对要序列化的对象自身调用一次,然后对对象的每个属性调用一次,然后如果对象的属性值是可迭代的,会继续对属性值中的每个属性再依次调用。
var a = {
b: 1,
c: [1,23,3]
}; JSON.stringify(a, function(k, v){
console.log('key:',k,' value:',v);
return v;
})

打印输出如下:

key:   value: {b: 1, c: Array(3)}
key: b value: 1
key: c value: (3) [1, 23, 3]
key: 0 value: 1
key: 1 value: 23
key: 2 value: 3

JSON.stringify的执行结果:

"{"b":1,"c":[1,23,3]}"

JSON.stringify还有第三个参数,可以指定缩进符,让生成的字符串更容易被阅读:

JSON.stringify(a, null, 2);

输出结果:

"{
"b": 1,
"c": [
1,
23,
3
]
}"

默认是空格缩进,所以2表示缩进两个空格,你也可以传入别的字符。


三、假值对象

这一点牵扯到了其他值向布尔值的强制类型转换。日常开发中我们经常用到如下所示类型的代码:

var a = '111';
if (a) {
...
}

if语句对a做了一个隐式强制类型转换,我们知道空字符串会被转换为false,非空就是true,包括'0'这种情况。

ES规范列举如下几种会转为假值的值:

  • undefined
  • null
  • false
  • +0, -0, NaN
  • ''

除了这几种值,我们可以认为别的情况都会被转为true。包括空对象{}。但是,还存在一种假值对象,会被转为false。

作者举了一个document.all的类数组对象,会被转为false。现实情况确实是这样。但是似乎这种假值对象并不是很多,多数作为坑存在,我觉得知道有这么一个东西存在就可以了。


四、parseInt()和Number()

  • paeseInt():解析字符串中的数字
  • Number():将字符串强制类型转换为数字

解析允许字符串中含有非数字字符,解析从左到右,遇到第一个非数字字符停止,返回第一个非数字字符之前的所有数字。

转换不允许字符串含有非数字字符,否则返回NaN。

这两种方式各有各的使用场景。


五、||和&&

在JS中,||和&&这两个运算符有一些特殊,如果接触过java、C等语言。我们可能会想当然的把它们称作逻辑运算符,返回值为true或false。但是在JS中,这两个运算符的返回值并不全是true和false,而是返回两个操作数中的一个。

var a = 1;
var b = "2";
var c = {};
var d = true; a || b; // 1
a && b; // "2" b || c; // "2"
b && c; // {} c || d; // {}
c && d; // true

在JS中,||和&&操作符会首先对第一个操作数执行判断,如果值不是布尔值,首先执行强制类型转换:

  • 对“||”而言,如果第一个操作数强制类型转换后为true,则直接返回第一个操作数,否则,直接返回第二个操作数。
  • 对“&&”而言,如果第一个操作数强制类型转换后为false,则直接返回第一个操作数,否则,直接返回第二个操作数。

所以,现在我们就能更好的理解如下所示的这种代码的执行机制到底是怎么回事了:

var a = '1';
var b = '2'; if (a && b) {
...
}

首先,(a && b)这个表达式我们知道返回值是'2',然后if语句对这个结果执行了隐式强制类型转换,转换后的结果为true。


六、宽松相等和严格相等

在了解了强制类型转换后,我们也就能对=====有一个更清晰的理解。

==允许在相等比较中进行强制类型转换,而===不允许。

《You dont know JS》强制类型转换的更多相关文章

  1. Js里面的强制类型转换

    js 和 PHP语言一样是弱类型语言.近期我也在看C语言,并没有传说中那么难,既是书中一再强调的指针部分,也没有那么夸张.至少是理论和语法理解起来不是很难.看起来凡是什么东西,不要总是被别人的话迷惑了 ...

  2. JavaScript学习10 JS数据类型、强制类型转换和对象属性

    JavaScript学习10 JS数据类型.强制类型转换和对象属性 JavaScript数据类型 JavaScript中有五种原始数据类型:Undefined.Null.Boolean.Number以 ...

  3. JS 数据类型转换-转换函数、强制类型转换、利用js变量弱类型转换

    1. 转换函数: js提供了parseInt()和parseFloat()两个转换函数.前者把值转换成整数,后者把值转换成浮点数.只有对String类型调用这些方法,这两个函数才能正确运行:对其他类型 ...

  4. JS在if中的强制类型转换

    JS在if中的强制类型转换 众所周知,JS在很多情况下会进行强制类型转换,其中,最常见两种是: 1.使用非严格相等进行比较,对==左边的值进行类型转换 2.在if判断时,括号内的值进行类型转换,转化为 ...

  5. JS中的“==”与强制类型转换

    JavaScript中有“==”与“===”,那么他们有何区别呢? 对于基本数据类型, ===  (!==)只有当两个变量的类型和值都相等时,才返回true:而 == (!=)则会对变量进行强制类型转 ...

  6. JS的类型转换,强制转换和隐式转换

    JS的类型转换 1.强制转换 通过String(),Number(),Boolean()函数强制转换 var str=123; var str1='123'; console.log(typeof s ...

  7. Js中的假值_ES5中定义的ToBoolean方法强制类型转换后值为false

    你不知道的Javascript(中)--ToBoolean javascript中的值可以分为以下两类: 1.可以被强制类型转换为false的值 2.其他(被强制类型转换为true的值) 假值---以 ...

  8. js字符串转换为数字的三种方法。(转换函数)(强制类型转换)(利用js变量弱类型转换)

    js字符串转换为数字的三种方法.(转换函数)(强制类型转换)(利用js变量弱类型转换) 一.总结 js字符串转换为数字的三种方法(parseInt("1234blue"))(Num ...

  9. JavaScript基础&实战(2)js中的强制类型转换、运算符、关系运算符、逻辑运算符、条件运算符

    文章目录 1.强制类型转换Number 1.1 代码 1.2 测试结果 2.进制表示 2.1 代码 2.2 测试结果 3.强制类型转换为Boolea 3.1 代码 3.2 测试结果 4.运算符 4.1 ...

随机推荐

  1. 初级版python登录验证,上传下载文件加MD5文件校验

    服务器端程序 import socket import json import struct import hashlib import os def md5_code(usr, pwd): ret ...

  2. 自动化构建工具--gulp的初识和使用

    gulp 首先:什么是gulp? gulp是前端开发过程中对代码进行构建的工具,是自动化项目的构建利器:她不仅能对网站资源进行优化,而且在开发过程中很多重复的任务能够使用正确的工具自动完成:使用她,我 ...

  3. loj#6235. 区间素数个数(min25筛)

    题意 题目链接 Sol min25筛的板子题,直接筛出\(g(N, \infty)\)即可 筛的时候有很多trick,比如只存\(\frac{N}{x}\)的值,第二维可以滚动数组滚动掉 #inclu ...

  4. python爬虫笔记----4.Selenium库(自动化库)

    4.Selenium库 (自动化测试工具,支持多种浏览器,爬虫主要解决js渲染的问题) pip install selenium 基本使用 from selenium import webdriver ...

  5. ubuntu禁止系统自动升级之界面操作

    ##第一步:首先找到System Settings,如下图所示: ##第二步:然后找到Solfware & Updates,如下图所示: ##第三步:点击Solfwate & Upda ...

  6. 生成项目目录结构(based on windows system)

    描述: 作为程序员,在工作中,我们经常会有需求,需要罗列出项目的结构图:如果手工来整理的话,太过浪费时间,其实我们可以借助tree命令来快速生成目录结构. 本文主要介绍一下,基于windows系统,如 ...

  7. clipChildren属性

    <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android=&quo ...

  8. 深入理解net core中的依赖注入、Singleton、Scoped、Transient(一)

    相关文章: 深入理解net core中的依赖注入.Singleton.Scoped.Transient(一) 深入理解net core中的依赖注入.Singleton.Scoped.Transient ...

  9. Mouse For Winpad

    Mouse For Winpad 用WIN10的平板模式玩游戏总会到一些兼容性问题,之前在推Re:LieF的时候就遇到了触屏不能像鼠标指针一样进行游戏,于是猜想一定是程序没进行标准化MFC的编程.于是 ...

  10. 关于p标签

    说p标签是不能嵌套div和p的,嵌套会被浏览器解析分离.但如果你使用了document.createElement创建div,再appendChild的话反而可以了.看来浏览器并不支持动态解析