1.位操作符
在 ECMAScript 中铐维,當(dāng)對數(shù)值應(yīng)用位操作符時,后臺會發(fā)生如下轉(zhuǎn)換過程:64 位的數(shù)值被轉(zhuǎn)換成 32位數(shù)值景埃,然后執(zhí)行位操作跪帝,最后再將 32 位的結(jié)果轉(zhuǎn)換回 64 位數(shù)值。這樣崎苗,表面上看起來就好像是在操作 32 位數(shù)值狐粱,就跟在其他語言中以類似方式執(zhí)行二進(jìn)制操作一樣舀寓。但這個轉(zhuǎn)換過程也導(dǎo)致了一個嚴(yán)重的副效應(yīng),即在對特殊的 NaN 和 Infinity 值應(yīng)用位操作時肌蜻,這兩個值都會被當(dāng)成 0 來處理互墓。
??在有符號位二進(jìn)制中,0為正值蒋搜,1為負(fù)值篡撵。
??位操作符是以二進(jìn)制進(jìn)行操作的,有如下幾種:
??1.按位非(NOT):按位非操作符由一個波浪線(~)表示豆挽,執(zhí)行按位非的結(jié)果就是返回數(shù)值的反碼育谬。例如:
var num1 = 25; // 二進(jìn)制為00000000000000000000000000011001
var num2 = ~num1; //二進(jìn)制為11111111111111111111111111100110
alert(num2); // -26
這里,對 25 執(zhí)行按位非操作帮哈,結(jié)果得到了-26膛檀。這也驗證了按位非操作的本質(zhì):操作數(shù)的負(fù)值減 1。
??2.按位與( AND):按位與操作符由一個和號字符(&)表示娘侍,它有兩個操作符數(shù)宿刮。從本質(zhì)上講,按位與操作就是將兩個數(shù)值的每一位對齊私蕾,都為時才為1僵缺,否則為0。
??3.按位或(OR):按位或操作符由一個豎線符號(|)表示踩叭,同樣也有兩個操作數(shù)磕潮。二進(jìn)制數(shù)的每一位對齊,全0為0容贝,有1為1.
??4.按位異或(XOR):操作符為(^)自脯,相同為0,相異為1.
??5.左移:左移操作符由兩個小于號(<<)表示斤富,這個操作符會將數(shù)值的所有位向左移動指定的位數(shù)膏潮。例如,如果將數(shù)值 2(二進(jìn)制碼為 10)向左移動 5 位满力,結(jié)果就是 64(二進(jìn)制碼為 1000000)焕参,代碼如下所示(左移不會影響操作數(shù)的符號位):
var oldValue = 2; // 等于二進(jìn)制的 10
var newValue = oldValue << 5; // 等于二進(jìn)制的 1000000,十進(jìn)制的 64
6.有符號右移:有符號的右移操作符由兩個大于號(>>)表示油额,這個操作符會將數(shù)值向右移動叠纷,但保留符號位(即正負(fù)號標(biāo)記),正數(shù)用0填充潦嘶,負(fù)數(shù)用1填充涩嚣。有符號的右移操作與左移操作恰好相反,即如果將 64 向右移動 5 位,結(jié)果將變回 2:
var oldValue = 64; // 等于二進(jìn)制的 1000000
var newValue = oldValue >> 5; // 等于二進(jìn)制的 10 航厚,即十進(jìn)制的 2
7.無符號右移:無符號右移操作符由 3 個大于號(>>>)表示顷歌,這個操作符會將數(shù)值的所有 32 位都向右移動。對正數(shù)來說幔睬,無符號右移的結(jié)果與有符號右移相同眯漩。但是對負(fù)數(shù)來說,情況就不一樣了溪窒。首先,無符號右移是以 0 來填充空位冯勉,而不是像有符號右移那樣以符號位的值來填充空位澈蚌。其次,無符號右移操作符會把負(fù)數(shù)的二進(jìn)制碼當(dāng)成正數(shù)的二進(jìn)制碼灼狰。而且宛瞄,由于負(fù)數(shù)以其絕對值的二進(jìn)制補(bǔ)碼形式表示,因此就會導(dǎo)致無符號右移后的結(jié)果非常之大交胚,如下面的例子所示:
var oldValue = -64; // 等于二進(jìn)制的 11111111111111111111111111000000
var newValue = oldValue >>> 5; // 等于十進(jìn)制的 134217726份汗,二進(jìn)制為000001111111111111111111111111110
2.布爾操作符
布爾操作符一共有 3 個:非(NOT)、與(AND)和或(OR)蝴簇。
??1.邏輯非:邏輯非操作符由一個嘆號(1睢)表示,可以應(yīng)用于 ECMAScript 中的任何值熬词。無論這個值是什么數(shù)據(jù)類型旁钧,這個操作符都會返回一個布爾值。
??如果操作數(shù)是 null互拾,返回 true歪今;
??如果操作數(shù)是 NaN,返回 true颜矿;
??如果操作數(shù)是 undefined寄猩,返回 true。
??2.邏輯與:邏輯與操作符由兩個和號(&&)表示骑疆,有兩個操作數(shù)田篇。
邏輯與操作可以應(yīng)用于任何類型的操作數(shù),而不僅僅是布爾值箍铭。在有一個操作數(shù)不是布爾值的情況下斯辰,邏輯與操作就不一定返回布爾值;此時坡疼,它遵循下列規(guī)則:
- 如果第一個操作數(shù)是對象彬呻,則返回第二個操作數(shù);
- 如果第二個操作數(shù)是對象,則只有在第一個操作數(shù)的求值結(jié)果為 true 的情況下才會返回該對象闸氮;
- 如果兩個操作數(shù)都是對象剪况,則返回第二個操作數(shù);
- 如果有一個操作數(shù)是 null蒲跨,則返回 null译断;
- 如果有一個操作數(shù)是 NaN,則返回 NaN或悲;
- 如果有一個操作數(shù)是 undefined孙咪,則返回 undefined。
邏輯與操作屬于短路操作巡语,即如果第一個操作數(shù)能夠決定結(jié)果翎蹈,那么就不會再對第二個操作數(shù)求值。
3.邏輯或:邏輯或操作符由兩個豎線符號(||)表示男公,有兩個操作數(shù)荤堪。
與邏輯與操作相似,如果有一個操作數(shù)不是布爾值枢赔,邏輯或也不一定返回布爾值澄阳;此時,它遵循下列規(guī)則: - 如果第一個操作數(shù)是對象踏拜,則返回第一個操作數(shù)碎赢;
- 如果第一個操作數(shù)的求值結(jié)果為 false,則返回第二個操作數(shù)速梗;
- 如果兩個操作數(shù)都是對象揩抡,則返回第一個操作數(shù);
- 如果兩個操作數(shù)都是 null镀琉,則返回 null峦嗤;
- 如果兩個操作數(shù)都是 NaN,則返回 NaN屋摔;
- 如果兩個操作數(shù)都是 undefined烁设,則返回 undefined。
與邏輯與操作符相似钓试,邏輯或操作符也是短路操作符装黑。也就是說,如果第一個操作數(shù)的求值結(jié)果為true弓熏,就不會對第二個操作數(shù)求值了恋谭。
3.乘性操作符
ECMAScript 定義了 3 個乘性操作符:乘法、除法和求模挽鞠。
?1.乘法:乘法操作符由一個星號(*)表示疚颊。
?在處理特殊值的情況下狈孔,乘法操作符遵循下列特殊的規(guī)則:
- 如果操作數(shù)都是數(shù)值,執(zhí)行常規(guī)的乘法計算材义,即兩個正數(shù)或兩個負(fù)數(shù)相乘的結(jié)果還是正數(shù)均抽,而如果只有一個操作數(shù)有符號,那么結(jié)果就是負(fù)數(shù)其掂。如果乘積超過了 ECMAScript 數(shù)值的表示范圍油挥,則返回 Infinity 或-Infinity;
- 如果有一個操作數(shù)是 NaN款熬,則結(jié)果是 NaN深寥;
- 如果是 Infinity 與 0 相乘,則結(jié)果是 NaN贤牛;
- 如果是 Infinity 與非 0 數(shù)值相乘惋鹅,則結(jié)果是 Infinity 或-Infinity,取決于有符號操作數(shù)的符號盔夜;
- 如果是 Infinity 與 Infinity 相乘负饲,則結(jié)果是 Infinity堤魁;
- 如果有一個操作數(shù)不是數(shù)值喂链,則在后臺調(diào)用 Number()將其轉(zhuǎn)換為數(shù)值,然后再應(yīng)用上面的規(guī)則妥泉。
2.除法:除法操作符由一個斜線符號(/)表示椭微。
與乘法操作符類似,除法操作符對特殊的值也有特殊的處理規(guī)則盲链。這些規(guī)則如下: - 如果操作數(shù)都是數(shù)值蝇率,執(zhí)行常規(guī)的除法計算,即兩個正數(shù)或兩個負(fù)數(shù)相除的結(jié)果還是正數(shù)刽沾,而如果只有一個操作數(shù)有符號本慕,那么結(jié)果就是負(fù)數(shù)。如果商超過了ECMAScript 數(shù)值的表示范圍侧漓,則返回 Infinity 或-Infinity锅尘;
- 如果有一個操作數(shù)是 NaN,則結(jié)果是 NaN布蔗;
- 如果是 Infinity 被 Infinity 除藤违,則結(jié)果是 NaN;
- 如果是零被零除纵揍,則結(jié)果是 NaN顿乒;
- 如果是非零的有限數(shù)被零除,則結(jié)果是 Infinity 或-Infinity泽谨,取決于有符號操作數(shù)的符號璧榄;
- 如果是 Infinity 被任何非零數(shù)值除特漩,則結(jié)果是 Infinity 或-Infinity,取決于有符號操作數(shù)的符號犹菱;
3.求模:求模(余數(shù))操作符由一個百分號(%)表示拾稳,用法如下:
var result = 26 % 5; // 等于 1
與另外兩個乘性操作符類似,求模操作符會遵循下列特殊規(guī)則來處理特殊的值: - 如果操作數(shù)都是數(shù)值腊脱,執(zhí)行常規(guī)的除法計算访得,返回除得的余數(shù);
- 如果被除數(shù)是無窮大值而除數(shù)是有限大的數(shù)值陕凹,則結(jié)果是 NaN悍抑;
- 如果被除數(shù)是有限大的數(shù)值而除數(shù)是零,則結(jié)果是 NaN杜耙;
- 如果是 Infinity 被 Infinity 除搜骡,則結(jié)果是 NaN;
- 如果被除數(shù)是有限大的數(shù)值而除數(shù)是無窮大的數(shù)值佑女,則結(jié)果是被除數(shù)记靡;
- 如果被除數(shù)是零,則結(jié)果是零团驱;
- 如果有一個操作數(shù)不是數(shù)值摸吠,則在后臺調(diào)用 Number()將其轉(zhuǎn)換為數(shù)值,然后再應(yīng)用上面的規(guī)則嚎花。
4.加性操作符
1.加法:加法操作符(+)
?如果兩個操作符都是數(shù)值寸痢,執(zhí)行常規(guī)的加法計算,然后根據(jù)下列規(guī)則返回結(jié)果:
- 如果有一個操作數(shù)是 NaN紊选,則結(jié)果是 NaN啼止;
- 如果是 Infinity 加 Infinity,則結(jié)果是 Infinity兵罢;
- 如果是-Infinity 加-Infinity献烦,則結(jié)果是-Infinity;
- 如果是 Infinity 加-Infinity卖词,則結(jié)果是 NaN巩那;
- 如果是+0 加+0,則結(jié)果是+0坏平;
- 如果是-0 加-0拢操,則結(jié)果是-0;
- 如果是+0 加-0舶替,則結(jié)果是+0令境。
不過,如果有一個操作數(shù)是字符串顾瞪,那么就要應(yīng)用如下規(guī)則: - 如果兩個操作數(shù)都是字符串舔庶,則將第二個操作數(shù)與第一個操作數(shù)拼接起來抛蚁;
- 如果只有一個操作數(shù)是字符串,則將另一個操作數(shù)轉(zhuǎn)換為字符串惕橙,然后再將兩個字符串拼接起來瞧甩。
??如果有一個操作數(shù)是對象、數(shù)值或布爾值弥鹦,則調(diào)用它們的 toString()方法取得相應(yīng)的字符串值肚逸,然后再應(yīng)用前面關(guān)于字符串的規(guī)則。對于 undefined 和 null彬坏,則分別調(diào)用 String()函數(shù)并取得字符串"undefined"和"null"朦促。
5.關(guān)系操作符
小于(<)、大于(>)栓始、小于等于(<=)和大于等于(>=)這幾個關(guān)系操作符用于對兩個值進(jìn)行比較务冕,這幾個操作符都返回一個布爾值。
與 ECMAScript 中的其他操作符一樣幻赚,當(dāng)關(guān)系操作符的操作數(shù)使用了非數(shù)值時禀忆,也要進(jìn)行數(shù)據(jù)轉(zhuǎn)換或完成某些奇怪的操作。以下就是相應(yīng)的規(guī)則落恼。
- 如果兩個操作數(shù)都是數(shù)值箩退,則執(zhí)行數(shù)值比較。
- 如果兩個操作數(shù)都是字符串领跛,則比較兩個字符串對應(yīng)的字符編碼值乏德。
- 如果一個操作數(shù)是數(shù)值撤奸,則將另一個操作數(shù)轉(zhuǎn)換為一個數(shù)值吠昭,然后執(zhí)行數(shù)值比較。
- 如果一個操作數(shù)是對象胧瓜,則調(diào)用這個對象的 valueOf()方法矢棚,用得到的結(jié)果按照前面的規(guī)則執(zhí)行比較。如果對象沒有 valueOf()方法府喳,則調(diào)用 toString()方法蒲肋,并用得到的結(jié)果根據(jù)前面的規(guī)則執(zhí)行比較。
- 如果一個操作數(shù)是布爾值钝满,則先將其轉(zhuǎn)換為數(shù)值兜粘,然后再執(zhí)行比較。
如果那個字符串不能被轉(zhuǎn)換成一個合理的數(shù)值呢弯蚜?比如:var result = "a" < 3; // false
孔轴,因為"a"被轉(zhuǎn)換成了 NaN,由于字母"a"不能轉(zhuǎn)換成合理的數(shù)值碎捺,因此就被轉(zhuǎn)換成了 NaN路鹰。根據(jù)規(guī)則贷洲,任何操作數(shù)與 NaN 進(jìn)行關(guān)系比較,結(jié)果都是 false晋柱。
6.相等操作符
ECMAScript 提供兩組操作符:相等和不相等——先轉(zhuǎn)換再比較优构,全等和不全等——僅比較而不轉(zhuǎn)換。
?1. 相等和不相等:
??null 和 undefined 是相等的雁竞,即null == undefined // 返回true
钦椭。
?2.全等和全不等:
??null === undefined 會返回 false,因為它們是不同類型的值碑诉。
7.條件操作符
variable = boolean_expression ? true_value : false_value;
8.賦值操作符
就是等號 =
9.逗號操作符
在用于賦值時玉凯,逗號操作符總會返回表達(dá)式中的最后一項,如下面的例子所示:var num = (5, 1, 4, 8, 0); // num 的值為 0