提問
相等運算符(==)是一個讓人頭痛的運算符,它的語法行為多變,不符合直覺。
請看下面的這個表達式,請問它們的值是多少。
0 == null
false == '0.0'
以及為什么?
破題
數據類型轉換表
ECMA規定了 == 運算符具體的處理,我將其內容整理,形成了如下的表格
類型 | boolean | string | number | symbol | object | null | undefined |
---|---|---|---|---|---|---|---|
boolean | === | Number(boolean) == string | Number(boolean) == number | Number(boolean) == symbol | Number(boolean) == object | Number(boolean) == null | Number(boolean) == undefined |
string | Number(boolean) == string | === | Number(string) == number | false | string == toPrimitive(object) | false | false |
number | Number(boolean) == number | number == Number(string) | === | false | number == toPrimitive(object) | false | false |
symbol | symbol == Number(boolean) | false | false | === | symbole == toPrimitive(object) | false | false |
object | object == Number(boolean) | toPrimitive(object) == string | toPrimitive(object) == number | toPrimitive(object) == symbol | === | false | false |
null | Number(boolean) == null | false | false | false | false | === | true |
undefined | Number(boolean) == undefined | false | false | false | false | true | === |
轉換表內容解析
以上的表格雖然表達的很清楚,但是我們翻閱的時候,可能會覺得繁瑣,所以我們在這里將上面的表格進行一次提煉整理。
我們在分析上面的內容的時候,發現以下規律
- null == undefined 結果為true
- null | undefined 與 其他類型比較均為 false
- string | number | symbol == object 會將使用toPrimitive將object轉換為原始類型數據,在進行比較(ps: 稍后會補一篇文章用來解釋toPrimitive的行為)
- symbol == string | number 比較均為 false
- boolean == number | string 比較會轉為 number
- string == number 比較會轉為 number
揭曉答案
現在我們回到前言中提到的問題,通過正文中的學習,我想我們可以快速而且非常自信的回答出答案了。
0 == null // false
false == '0.0' // true
怎么樣,小伙伴們是不是都回答正確了呢。
下面讓我們來具體的分析下上面兩道題。
-
0 == null
考的知識點是 null 與 非 null | undefined 比較返回均為false
-
false == '0.0'
這道題需要進行以下三步,方能得到答案
1:
Number(false) == '0.0'
得到0 == '0.0
2:
0 == Number('0.0')
得到0 == 0.0
3:
0 === 0.0 // true
ECMA算法參考
ReturnIfAbrupt(x).
ReturnIfAbrupt(y).
If Type(x) is the same as Type(y), then
Return the result of performing Strict Equality Comparison x === y.
If x is null and y is undefined, return true.
If x is undefined and y is null, return true.
If Type(x) is Number and Type(y) is String, return the result of the comparison x == ToNumber(y).
If Type(x) is String and Type(y) is Number, return the result of the comparison ToNumber(x) == y.
If Type(x) is Boolean, return the result of the comparison ToNumber(x) == y.
If Type(y) is Boolean, return the result of the comparison x == ToNumber(y).
If Type(x) is either String, Number, or Symbol and Type(y) is Object, then return the result of the
comparison x == ToPrimitive(y).
If Type(x) is Object and Type(y) is either String, Number, or Symbol, then return the result of the comparison ToPrimitive(x) == y.
Return false.