摘要:顯然,相等判斷是基于數(shù)字比較的,而條件判斷是基于布爾值。嚴(yán)格相等嚴(yán)格相等的邏輯相對簡單粗暴,如果類型不同,就不考慮隱式轉(zhuǎn)換了,直接為假。
JavaScript 中大概有這幾種 “類型”:
undefined
null
string
boolean
number
object
function
之所以在 “類型” 上加了雙引號,是因為嚴(yán)格來說,null 的類型是 object。但本文討論的主題包括了關(guān)于 null 的類型轉(zhuǎn)換,它和 object 不同,所以多帶帶列出來了。這點(diǎn)請根據(jù)上下文強(qiáng)行區(qū)分一下,不是bug、不是bug、不是bug。
有趣的例子"0" == 0; // true 0 == ""; // true "0" == ""; // false
這里展示的是相等比較的非傳遞性。即,如果有 a == b, b == c,并不代表 a == c。
如果說
"1" == true; "0" == false;
這兩個是常識,那對于一些特殊的字符串,你能正確判斷嗎?
"001" == true; "002" == false; // 注意! "0x0" == false; " " == false;非嚴(yán)格相等(==)
當(dāng)使用 == 比較,并且兩側(cè)的類型不同時,會觸發(fā)隱式類型轉(zhuǎn)換。標(biāo)準(zhǔn)中定義的轉(zhuǎn)換規(guī)則很長,其核心就是,1、類型不同時,盡量轉(zhuǎn)成 數(shù)字 比較;2、特例。(類型相同就按該類型的值判斷,不特殊說明了,難道 "123" 還能等于 "456" 不成?)
關(guān)于特例,其實(shí)也就是 null 和 undefined 。也就是說,以下幾個表達(dá)式是永遠(yuǎn)為 true 的。
undefined == null; null == undefined; NaN != NaN; // 注意! null != 非null; // 注意!null 與非 null 值永遠(yuǎn)是不等的
所以也不需要再去深追為什么 undefined 和 null 是相等的,因為按照“規(guī)則”已經(jīng)無法解釋了,這是一種“約定”。OK,剩下的情況是轉(zhuǎn)數(shù)字。
null 的數(shù)值是 0
undefined 的數(shù)值是 NaN
true 是 1,false 是 0
至于字符串,嗯,有點(diǎn)復(fù)雜
object:調(diào)用 toString 或 valueOf 后轉(zhuǎn)成基本類型,再轉(zhuǎn)數(shù)字
第一條,在這里沒用,因為涉及到 null 的比較時,除非 null == null,其他情況都是不等的。即
null != 0;
第二條,在這里沒用,因為涉及到 NaN 的比較時,都是不等。
第三條,有點(diǎn)用,很有用!
1 == true; // 對 2 == true; // 錯!
第四條,麻煩。80% 情況下,對于 "123" 轉(zhuǎn)成 123,"abc" 轉(zhuǎn)成 NaN,"" 轉(zhuǎn)成 0,這三條記住就可以了。
"123" == 123; "" == 0; "abc"; // 轉(zhuǎn)成數(shù)值是 NaN
另外的情況,由于字符串的組合形式各種各樣,很難三言兩語總結(jié)完,大致有:
空白字符串轉(zhuǎn)成 0," " == 0
十六進(jìn)制、八進(jìn)制正常轉(zhuǎn)換,"0xff" == 255
數(shù)字字符串會忽略首尾空白字符,正常轉(zhuǎn)," 123 " == 123
數(shù)字字符和其他字符混合時,轉(zhuǎn)成 NaN,如 "123abc"
現(xiàn)在回頭去看“有趣的例子”,是不是一目了然。(嗯,不謝)
條件判斷暫且把 if - else 和 condition ? a : b; 中的判斷情況稱為條件判斷吧。(場景還有取反、for、while 等)
等于 true 的值一定是 truthy,但等于 false 的值不一定是 falsy 。
例
new Boolean(false) == false; // 這個沒問題吧? new Boolean(false) ? "a" : "b"; // 表達(dá)式的值是 "a"!
只能說,條件判斷中對真假的判定和相等判斷是不一樣的。 顯然,相等判斷是基于數(shù)字比較的,而條件判斷是基于布爾值。
關(guān)于布爾值的轉(zhuǎn)換規(guī)則:
null, undefined, NaN 都是 false
字符串,僅當(dāng)空字符串("")時為 false,其他都是 true
object,都是 true (僅 null 除外)
我見過其他一些相等判斷的技巧:
!!x == true; +x == 123;
取反操作會把變量強(qiáng)轉(zhuǎn)成 boolean;一元 + 會把變量強(qiáng)轉(zhuǎn)成 number。
也見過一些用的不太合適的地方(?):
if (!!x) // ...
在條件判斷中本身會做強(qiáng)轉(zhuǎn)的操作,為了可讀性?不見得有提高。
嚴(yán)格相等(===)嚴(yán)格相等的邏輯相對簡單粗暴,如果類型不同,就不考慮隱式轉(zhuǎn)換了,直接為假。如果類型相同:
布爾、數(shù)字、字符串就看字面值是否相等
object,看引用是否相同
主要是考慮什么時候用 ==,什么時候用 === 。
很簡單,只有在要求類型相同時,才用 ===,否則用 ==
有些場景的確只有非嚴(yán)格相等才能做,比如
var b = new Boolean(false); b === false // 竟然是錯的 b == false // 對 b ? "a" : "b" // 竟然是 "a"
結(jié)論就是當(dāng)涉及到對象比較時,稍微斟酌一下。而對于像 typeof x 它一定會返回 string,這時用 == 比較就更合適一些。
小結(jié)涉及到 == 比較,并且需要隱式轉(zhuǎn)換時,會轉(zhuǎn)成 number。
涉及到條件判斷,自然是轉(zhuǎn)成 boolean。
涉及到二元 +、- 等數(shù)值計算時,從左至右優(yōu)先轉(zhuǎn)成 number,除非是遇到 string,則做字符串拼接操作。
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/91574.html
摘要:等同于等同于其他類型和布爾類型之間的比較如果是布爾類型,則返回的結(jié)果。 showImg(https://segmentfault.com/img/bVburFq?w=796&h=398); 前言 JavaScript作為一門弱類型語言,我們在每天的編寫代碼過程中,無時無刻不在應(yīng)用著值類型轉(zhuǎn)換,但是很多時候我們只是在單純的寫,并不曾停下腳步去探尋過值類型轉(zhuǎn)換的內(nèi)部轉(zhuǎn)換規(guī)則,最近通過閱讀你...
摘要:等同于等同于其他類型和布爾類型之間的比較如果是布爾類型,則返回的結(jié)果。 showImg(https://segmentfault.com/img/bVburFq?w=796&h=398); 前言 JavaScript作為一門弱類型語言,我們在每天的編寫代碼過程中,無時無刻不在應(yīng)用著值類型轉(zhuǎn)換,但是很多時候我們只是在單純的寫,并不曾停下腳步去探尋過值類型轉(zhuǎn)換的內(nèi)部轉(zhuǎn)換規(guī)則,最近通過閱讀你...
摘要:等同于等同于其他類型和布爾類型之間的比較如果是布爾類型,則返回的結(jié)果。 showImg(https://segmentfault.com/img/bVburFq?w=796&h=398); 前言 JavaScript作為一門弱類型語言,我們在每天的編寫代碼過程中,無時無刻不在應(yīng)用著值類型轉(zhuǎn)換,但是很多時候我們只是在單純的寫,并不曾停下腳步去探尋過值類型轉(zhuǎn)換的內(nèi)部轉(zhuǎn)換規(guī)則,最近通過閱讀你...
本篇文章主要是講述在JavaScript中判斷兩個值相等,不要認(rèn)為很簡單,要注意的是在JavaScript中存在4種不同的相等邏輯。 ECMAScript 是 JavaScript 的語言規(guī)范,在ECMAScript 規(guī)范中存在四種相等算法,如下圖所示: 上圖中每個依次寫下來,很多前端應(yīng)該熟悉嚴(yán)格相等和非嚴(yán)格相等,但對于同值零和同值卻不熟悉,現(xiàn)在就依次下面四種方法。 同值 同值零 非...
閱讀 3650·2021-09-22 15:15
閱讀 3555·2021-08-12 13:24
閱讀 1309·2019-08-30 15:53
閱讀 1816·2019-08-30 15:43
閱讀 1178·2019-08-29 17:04
閱讀 2792·2019-08-29 15:08
閱讀 1573·2019-08-29 13:13
閱讀 3084·2019-08-29 11:06