運算符
+
bool都被轉成數字了
true + true // 2
1 + true // 2
如果有字符串,會先進行串接
'3' + 4 + 5 // "345" -> '3' + 4 = '34' + 5 = '345'
3 + 4 + '5' // "75" -> 3 + 4 = 7 + '5' = '75'
只有+會重載(根據參數 / 運算子)不同,決定不同語法行為
其他 - * / 都是將字符串轉成數值再計算
和對象相加
會把對象轉為原始類型
var obj = { p: 1 };
obj + 2 // "[object Object]2"
轉成原始類型的過程:
- 調用valueOf()
- 再調用toString()
對象的toString()默認返回[object object]
可以利用重寫valueOf或toString來使對象在運算中得到想要的結果
Date對象是例外,先執行toString()->valueOf()var obj = { valueOf: function () { return 1; } }; obj + 2 // 3
取餘 %
符號由第一個運算子決定
-1 % 2 // -1
1 % -2 // 1
为了得到负数的正确余数值,可以先使用绝对值函数。
// 错误的写法
function isOdd(n) {
return n % 2 === 1;
}
isOdd(-5) // false
isOdd(-4) // false
// 正确的写法
function isOdd(n) {
return Math.abs(n % 2) === 1;
}
isOdd(-5) // true
isOdd(-4) // false
自增/減
唯一有side effect的運算符(會改變變量)
++i -> 先自增1再執行語句
i++ -> 執行完語句再自增1
var i = 1, j = 1;
++i + 1 // 3
j++ + 1 // 2
數值運算符 + / -
一元運算符,把任何值轉為數值(和Number()相同)
- 轉成正數, - 轉成負數
+true // 1
+[] // 0
-true // -1
指數運算符 **
2 ** 4 // 16 -> 2 ^ 4
右結合,而不是左結合
2 ** 3 ** 4 // 2 ** (3 ** 4)
NaN比較
这里需要注意与NaN的比较。任何值(包括NaN本身)与NaN使用非相等运算符进行比较,返回的都是false。
1 > NaN // false
1 <= NaN // false
'1' > NaN // false
'1' <= NaN // false
NaN > NaN // false
NaN <= NaN // false
undifined vs null
兩者和自身嚴格相等
undefined === undefined // true
null === null // true
兩者只有和對方或自身做比較時才會返回true,否則都是false
undefined == undefined // true
null == null // true
undefined == null // true
false == null // false
false == undefined // false
0 == null // false
0 == undefined // false
对于两个对象的比较,严格相等运算符比较的是地址,而大于或小于运算符比较的是值。
布爾運算符
&&
如果第一个运算子的布尔值为true,则返回第二个运算子的值(注意是值,不是布尔值);如果第一个运算子的布尔值为false,则直接返回第一个运算子的值,且不再对第二个运算子求值。
't' && '' // ""
't' && 'f' // "f"
't' && (1 + 2) // 3
'' && 'f' // ""
'' && '' // ""
var x = 1;
(1 - 1) && ( x += 1) // 0
x // 1
且运算符可以多个连用,这时返回第一个布尔值为false的表达式的值。如果所有表达式的布尔值都为true,则返回最后一个表达式的值。
true && 'foo' && '' && 4 && 'foo' && true
// ''
1 && 2 && 3
// 3
跳过第二个运算子的机制,被称为“短路”。
||
如果第一个运算子的布尔值为true,则返回第一个运算子的值,且不再对第二个运算子求值;如果第一个运算子的布尔值为false,则返回第二个运算子的值。
機制與 && 類似,差別在於 && 返回第一個false的值或是最後一個值(如果全部為true)
|| 返回第一個為true的值,如果全false,返回最後一個
false || 0 || '' || 4 || 'foo' || true
// 4
false || 0 || ''
// ''
二進制運算符
- |
- &
- ~ not,取反
- ^ xor,異或,不相同
- <<
- >>
- >>> 頭部補零右移運算符
位運算符處理每一個比特位,但是只對整數起作用,非整數的會先轉成整數
JavaScript 内部,数值都是以64位浮点数的形式储存,但是做位运算的时候,是以32位带符号的整数进行运算的,并且返回值也是一个32位带符号的整数。
i = i | 0 // 将i(不管是整数或小数)转为32位整数。
|
兩個二進制只要有一個1,就返回1
0 | 3 //3 -> 00 | 11
不適合用做超過32位最大整數2147483647
取整
2147483649.4 | 0;
// -2147483647
&
两个二进制位之中只要有一个位为0,就返回0,否则返回1。
0 & 3 // 0
~
~ 3 // -4
(負)補碼取值: -1,再取反
0011 -> (~取反)-> 1100 -> (-1) -> 1011 -> 取反 -> 0100 -> 取值 -> 4 -> 加上負號 -> -4
省略的記法:
自身加一,然後取負數
~3 => 4, ~ -2 => 1, ~ -3 => 2
連續取反兩次,得到自身 -> 取整效果
對字符串取反,會先用Number轉成整數
^
可以用來交換變量(最快的方法)
var a = 10;
var b = 99;
a ^= b, b ^= a, a ^= b;
// a ^= b -> 105
// b ^= a -> 10
// a ^= b; -> 99
a // 99
b // 10
void
void运算符的作用是执行一个表达式,然后不返回任何值,或者说返回undefined。
void 0 // undefined
void(0) // undefined
void 4 + 7 // NaN -> 實際執行(void 4) + 7 -> undefined + 7 -> NaN
void (4 + 7) // undefined
主要用途是避免跳轉
<a href="http://example.com" onclick="f(); return false;">点击</a>
會先執行onClick,由於onClick返回false,所以不會跳轉
如果用void
<a href="javascript: void(f())">文字</a>
提交表單不跳轉
<a href="javascript: void(document.form.submit())">
提交
</a>