(Day8) 隐含转型 - 转成 Boolean & 宽松相等 vs 严格相等

前言

上一篇介绍了数字型别、字串型别的隐含转型,接下来介绍剩余的隐含转行,剩余隐含转型大约分成以下三种:

  • 隐含转型 : 转成 Boolean
  • 运算子 || 与 &&
  • 宽松相等(Loose Equals) vs 严格相等(Strict Equals)

隐含转型 : 转成 Boolean

关於转成布林值这一块,其实大多都是用在判断式的条件判断中,当条件判断成立,条件判断会透过隐含转型转成 true 因此条件下的程序码才能被执行, 例如:

  • if() 中的条件判断。
  • for( xx; xx; xx; ) 中,第二句的条件判断。
  • while() 中的条件判断。
  • xx ? OO1 : OO2 三元运算中的第一个条件判断。
  • 逻辑运算子中 ||&& 最左边的操作,会被转换。

接下来同样用程序码来看看

var a = 666
var b = 'test'
var c  
var d = null
if (a) { 
	// true
	console.log('执行成功');		// 执行成功
}
while (c) { 
	// false
	console.log('不执行');
}

d ? a : b // 'test' 
// d 被转成 false ,因此执行 b 

if ((a && d) || c) {
	//fasle
	console.log('不执行');		
} 

上面比较特别的就是 逻辑运算子 ||&& 这部分接下来会再说明。

逻辑运算子 || 与 &&

实做中我们很常用到判断式搭配 ||&& ,例如

var width = 768 
var fontSize = 16
if( width >= 1200 || fontSize === 16 ){
    xxx
}

这会让我们有种错觉 ||&& 运算子就是用来判断 truefalse 的方法,然而我们在上面 『隐含转型 : 转成 Boolean 』这部分就有提到, if() 中的判断式会被 JavaScript 根据是否达成,转成 truefalse , 也因此 ||&& 运算子不是单纯判断 truefalse 的方法,而这两个运算子语法的功能实际上是 : 在前後运算元中选择一个使用,这边也使用程序码当作范例:

var a = 123;
var b = "test";
var c = null;

a || b;		// 123
a && b;		// "test"

c || b;		// "test"
c && b;		// null

根据 MDN 文件描述:

&& 的状况是当第一个操作 是 false 时,&& 会回传第一个运算子,反之第一个是 true 回传第二个运算子,因此在判断式中使用 && 是必须两个条件都是 true 判断式才会被执行。

|| 运算子正好相反,当第一个操作 是 false|| 会回传第二个运算子,反之第一个是 true 时,|| 便会回传第一个操作结果,因此在判断式中使用 || 指要一个条件达成 true ,判断式就会被执行。

宽松相等(Loose Equals) vs 严格相等(Strict Equals)

在 JavaScript 中使用 === 比较运算子,我们称做 严格相等(Strict Equals),使用这种方法做对比并不会执行隐含转型的动作。

而使用 == 比较运算子做对比,称做 宽松相等(Loose Equals),使用这种方法做对比则会执行 隐含转型 的动作,比如这个范例:

'123' == 123 //true  字串 123 会被隐含转型 
'123' === 123 //false  两者型别不同

那麽关於 == 运算子在转型上是否有什麽规则?

这边可以透过 MDN 的文件来了解其规则

宽松相等

接者同样使用程序码当作范例:

1 == 'true' //false

从上面图表会发现,字串对上数字是 ToNumber(A) === B ,也就是两者都会转换成数字型别做对比。

[1,2,3] == '1,2,3' //true

阵列属於物件的一种,按照图表会是 ToPrimitive(A) == B ,按照 MDN 文件说明

ToPrimitive(A) 尝试从物件转换成原生值,透过尝试对 A 使用 A.toString 和 A.valueOf 方法。

也就是 [1,2,3] 会被 toString() 转成字串 。

false == '0' // true

布林对字串会是 ToNumber(A) === ToNumber(B) 两者都会被成数字,结果都是0 。

true == 'true' //false

同上布林对字串会是 ToNumber(A) === ToNumber(B) ,字串 'true' 也会被 ToNumber() 转换,转换後是 NaN

最後关於宽松相等,网路上也有人整理满完整的图表,这边也分享一下:
https://thomas-yang.me/projects/oh-my-dear-js/

参考资料


<<:  使用storyboard实现代理功能

>>:  AE极光制作1-Day7

Day30 - Windows 提权(1)-Unquoted Service Paths、修改服务提权

假设我们取得受害主机的 shell (cmd.exe 或 powershell)可以根据自己的需求取...

【Day 4】机器学习基本功(二) --- Regression

如何找到一个函式(function)?(上) 接下来会以李宏毅老师在影片中讲的例子来做说明整理。 寻...

学习资源

Golang 学习资源 昨天几乎整晚没睡,小屁孩疑似玫瑰疹,每半小时就起来一次,目前肉体跟灵魂已经分...

Day23:今天来聊一下Hacking Web Applications

Web application hacking是透过application的图形web介面操纵应用程...

Day03【JS】立即呼叫函式 IIFE

IIFE 全称为 Immediately Invoked Function Expression 中...