JavaScript | 深度剖析4大数据类型转换规则

智数银月引
• 阅读 1424

JavaScript | 深度剖析4大数据类型转换规则

0 / 把其他数据类型转换为Number类型

(1)指定需要转换为Number的

1、Number(value)

2、parseInt(string, radix)/parseFloat(string)

Number转换机制

把其他类型(string/boolean/null/undefined/symbol/bigint/object)使用Number转换为数字:

1、字符串中只要出现非有效数字,结果就是NaN

2、Number(true) 是1,Number(false) 是0

3、Number(null)是0,Number(undefined)是NaN

4、Number(Symbol('A')) 报错

5、Number(BigInt(10)) 是数字

6、对象变为数字:先调取Symbol.toPrimitive 获取原始值,没有再通过valueOf获得原始值;如果没有原始值,再调取toString变为字符串,最后把字符串转为数字

JavaScript | 深度剖析4大数据类型转换规则

△ 图1.1_Number的转换

parseInt/parseFloat转换机制

parseInt转换机制:从字符串左侧第一个字符开始,查找有效数字字符(遇到非有效数字字符就停止查找,不管后面是否还有数字都不要了),把找到的有效数字字符转换为数字,如果一个都没找到结果就是NaN

parseFloatparseInt多识别一个小数点

(2)隐式转换

1、isNaN(value),其他数据类型先通过Number转为数字类型

2、数学运算:+-*/%。数学运算,其他数据类型先用Number转换为数字类型再计算(特殊情况:+ 作为斜杠青年,当遇到字符串时,是字符串拼接)

3、在==比较时,有些值需要转为数字再进行比较

4、……

(3)练习题
parseInt("")
Number("")
isNaN("")
parseInt(null)
Number(null)
isNaN(null)
parseInt("12px")  
Number("12px")
isNaN("12px")
parseFloat("1.6px")+parseInt("1.2px")+typeof parseInt(null)
isNaN(Number(!!Number(parseInt("0.8"))))
typeof !parseInt(null) + !isNaN(null)

△ 其他数据类型转换为数字类型

L1parseInt("") 没有找到有效数字字符=> NaN

L2Number("") => 0

L3isNaN("") => isNaN 方法调用的是 Number 转换数据类型 => false

L4parseInt(null) => parseInt("null") => NaN

L5Number(null) =>0

L6isNaN(null) => false

L7parseInt("12px") => 12

L8Number("12px") => NaN

L9isNaN("12px") => true

L10parseFloat("1.6px")+parseInt("1.2px")+typeof parseInt(null)

=> typeof parseInt(null) => typeof NaN => "number"

=> 1.6 + 1 + "number"

=> "2.6number"

加号左右两边出现字符串,此时加号变为字符串拼接(有特殊性),如果出现对象也会变成字符串拼接,原本应该是把对象转为数字,但是对象要先转换为字符串,则遇到加号字符串就变成字符串拼接了

L11isNaN(Number(!!Number(parseInt("0.8"))))

=> parseInt("0.8") => 0

=> !!Number(0) => false

=> Number(false) => 0

=> isNaN(0) => false

L12typeof !parseInt(null) + !isNaN(null)

=> typeof !NaN + !false

=> typeof true + true

=> "boolean" + true

=> "booleantrue"

let result = 10+false+undefined+[]+'Tencent'+null+true+{};
console.log(result);

△ 答案是?

10+false+undefined+[]+'Tencent'+null+true+{}

=> 10 + false 没有遇到字符串和对象,数学运算:10+0 => 10

=> 10 + undefined => 10 + NaN => NaN

=> NaN + [] =>"NaN"

对象数据类型转换为数字:先转换为字符串再转换为数字

在转换为字符串后,遇到了加号=>字符串拼接

=>"NaN" + 'Tencent' +null+true+{}

=> "NaNTencentnulltrue[object Object]"

链接:"+" 的斜杠身份:数学运算,字符串拼接

(4)思考题
let arr = [10.18, 0, 10, 25, 23];
arr = arr.map(parseInt);
console.log(arr);

△ 思考题

1 / 把其他数据类型转为字符串

(1)显式转换

1、toString()

2、String()

其他数据类型(number/boolean/null/undefined/symbol/bigint/object)转换为字符串,一般都是直接用""引号包起来,只有{}普通对象调取toString()方法。调取的是Object.prototype.toString()方法(返回值:"[object Type]"),不是转换字符串,而是检测数据类型的:({id:"zhaoxiajingjing"}).toString() => "[object Object]"

JavaScript | 深度剖析4大数据类型转换规则

△ 图1.2_其他数据类型转换为字符串

(2)隐式转换(一般调取toString方法)

1、加号运算时候,如果有一边出现字符串,则是字符串拼接

2、把对象转为数字:需要先调用toString()转换为字符串,再去转换为数字

3、基于alert/confirm/prompt/document.write...这些方法输出内容,都是先把内容转化为字符串,再输出的

4、……

3 / 把其他数据类型转换为布尔

把其他类型(string/number/null/undefined/symbol/bigint/object)转换为布尔类型:

只有5个值会变成布尔类型的false:空字符串/0/NaN/null/undefined,其他都是true

(1)其他数据类型转换为布尔

1、!转换为布尔值后取反

2、!!转换为布尔类型

3、Boolean(value)

(2)隐式转换

在循环或者条件判断中,条件处理的结果就是布尔类型值

4 / 在==比较时,数据类型转换的规则

(1)需要注意的点

1、{}=={} false 对象数据类型比较的是堆内存地址

2、[]==[] false 对象数据类型比较的是堆内存地址

3、NaN==NaN false

(2)类型不一样的转换规则

1、 null==undefined true 其他数据类型的值与null/undefined都不相等

null===undefined false 它俩类型不一样

2、字符串==对象 把对象转换为字符串

3、剩下的,如果==两边数据类型不一致,需要转换为<u>数字</u>再进行比较

(3) 题
console.log([] == false);
console.log(![] == false);

△ 比较 ==

[] == flase

类型不一样,需要转换为数字再进行比较:隐式转换

1、对象转换为数字:先toString转换为字符串(先基于Symbol.toPrimitive获得原始值,没有的话基于valueOf获得原始值,没有原始值再去toString),在转换为数字

2、[]=>""=>0

3、false=>0 true=>1

4、结果是:[]==false => 0==0 => true

![]==false

运算符优先级:!==的要高

1、![] 把数组转换为布尔类型,再取反:!true => false

其他数据类型转换为布尔类型,是false的只有5个:空字符串/0/NaN/null/undefined,其他都是true

2、结果是:false == false => true

5 / 思考题-题解

let arr = [10.18, 0, 10, 25, 23];
arr = arr.map(parseInt);
console.log(arr);

△ 答案是?

考点:

① 数组map方法的使用

② parseInt方法的使用

arr = arr.map(function (item, index){
    // 形参:数组中的元素,索引
    // 循环遍历数组中的每一项,就会触发这个回调函数
    // 并返回一个新的数组
});

△ 数组map的用法

parseInt(string, radix)

解析一个字符串并返回指定基数的十进制整数,基数超过radix范围的都是返回NaN

radix 是2-36之间的整数,表示被解析字符串的基数。0或者不写,表示十进制

如果string是以0x开头的,则需要把结果转为16进制,不是10进制的

如何把一个值转换为十进制

147 是八进制 => 十进制

[位权值:每一位的权重,个位是0、十位是1……]

1*8^3+4*8^2+7*8^0

12.3(四进制)=>十进制

1*4^1+2*4^2+3*4^-1

4^0 =>1

4^1=>4

4^2=>16

4^-1 => 1/4

4^-2=> 1/(4*4)

好了,这道题:

let arr = [10.18, 0, 10, 25, 23];
arr = arr.map(parseInt);
console.log(arr);
//=======
arr = arr.map(function (item, index){});
parseInt(string, radix)
//=======
parseInt('10.18', 0);
parseInt('0', 1);
parseInt('10', 2);
parseInt('25', 3);
parseInt('23', 4);

△ 运算结果?

parseInt('10.18', 0);

① 从字符串左侧第一个字符开始查找

② 找到符合radix进制的值(遇到不合法的就停止查找)

③ 把找到的有效字符串变为数字,按照radix的进制数转换为十进制

radix取值范围:2~36,是0或者不写,为十进制

=> radix:0,按照十进制找有效字符:'10'

=> 结果是:转为十进制的数字:10

parseInt('0', 1); radix 取值范围;2~36

=> 结果是: NaN

parseInt('10', 2);

=> 找到radix:2 二进制的有效字符:10

=> 转为十进制:1*2^1+0*2^0

=> 结果是:2

parseInt('25', 3);

=> 找到radix:3 三进制的有效字符:2

=>转为十进制: 2*3^0

=> 结果是: 2

parseInt('23', 4);

=> 找到radix:4 四进制的有效字符:23

=> 转为十进制: 2*4^1+3*4^0

=> 结果是:11

所以结果:[10, NaN, 2, 2, 11]

注意parseFloat 没有第二个参数radix

- end -

JavaScript | 深度剖析4大数据类型转换规则

点赞
收藏
评论区
推荐文章
blmius blmius
4年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
Oracle 分组与拼接字符串同时使用
SELECTT.,ROWNUMIDFROM(SELECTT.EMPLID,T.NAME,T.BU,T.REALDEPART,T.FORMATDATE,SUM(T.S0)S0,MAX(UPDATETIME)CREATETIME,LISTAGG(TOCHAR(
Wesley13 Wesley13
4年前
MySQL部分从库上面因为大量的临时表tmp_table造成慢查询
背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
Stella981 Stella981
4年前
List的Select 和Select().tolist()
List<PersondelpnewList<Person{newPerson{Id1,Name"小明1",Age11,Sign0},newPerson{Id2,Name"小明2",Age12,
Wesley13 Wesley13
4年前
FLV文件格式
1.        FLV文件对齐方式FLV文件以大端对齐方式存放多字节整型。如存放数字无符号16位的数字300(0x012C),那么在FLV文件中存放的顺序是:|0x01|0x2C|。如果是无符号32位数字300(0x0000012C),那么在FLV文件中的存放顺序是:|0x00|0x00|0x00|0x01|0x2C。2.  
Wesley13 Wesley13
4年前
mysql设置时区
mysql设置时区mysql\_query("SETtime\_zone'8:00'")ordie('时区设置失败,请联系管理员!');中国在东8区所以加8方法二:selectcount(user\_id)asdevice,CONVERT\_TZ(FROM\_UNIXTIME(reg\_time),'08:00','0
Wesley13 Wesley13
4年前
PHP创建多级树型结构
<!lang:php<?php$areaarray(array('id'1,'pid'0,'name''中国'),array('id'5,'pid'0,'name''美国'),array('id'2,'pid'1,'name''吉林'),array('id'4,'pid'2,'n
Wesley13 Wesley13
4年前
Java日期时间API系列36
  十二时辰,古代劳动人民把一昼夜划分成十二个时段,每一个时段叫一个时辰。二十四小时和十二时辰对照表:时辰时间24时制子时深夜11:00凌晨01:0023:0001:00丑时上午01:00上午03:0001:0003:00寅时上午03:00上午0
Stella981 Stella981
4年前
Django中Admin中的一些参数配置
设置在列表中显示的字段,id为django模型默认的主键list_display('id','name','sex','profession','email','qq','phone','status','create_time')设置在列表可编辑字段list_editable
Python进阶者 Python进阶者
2年前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这
智数银月引
智数银月引
Lv1
时间会融化掉所有的尖锐。
文章
3
粉丝
0
获赞
0