涉及位運算的運算符如下表所示:?
位運算的運算律:
?
負數的位運算
首先,我們要知道,在計算機中,運算是使用的二進制補碼,而正數的補碼是它本身,負數的補碼則是符號位不變,其余按位取反,最后再+ 1 +1+1得到的, 例如:
15 ,原碼:00001111? 補碼:00001111?
? 15 ,原碼:10001111? ? 補碼:11110001?
那么對于負數的位運算而言,它們的操作都是建立在補碼上的,得到的運算結果是補碼,最后將補碼結果轉化成一個普通的十進制數結果。
但需要注意的是,對于有符號數的右移操作,不同的處理器架構可能有不同的規定。在某些架構中(如x86)
對有符號數執行算術右移(arithmetic right shift),則高位空出來的位置會補上符號位;
對于無符號數的右移操作,所有架構都遵循相同的規則:高位空出來的位置會補0。
例如對于? 15 ,其補碼為11110001 右移一位( ? 15 > > 1 )得到的是11111000 即? 8 其他的同理。
在大多數現代處理器上,無論是有符號數還是無符號數,左移操作總是將空出來的低位補0。
位運算的應用
位運算實現乘除法
將x左移一位實現× 2 將x 右移一位實現÷ 2
a < < 1 ≡ a ? 2?
a > > 1 ≡ a / 2? ?
兩數交換
void swap(int &a,int &b){a ^= b;b ^= a;a ^= b;}
剖析其原理,對于a = a ∧ b ,則b = b ∧ ( a ∧ b )
根據交換律以及異或性質,得b = b ∧ b ∧ a = 0 ∧ a = a
同理a = ( a ∧ b ) ∧ a = 0 ∧ b = b? ?這樣就實現了交換操作。
位運算判斷奇偶數
我們知道,在二進制中,最低位決定了是奇數還是偶數,所以我們可以提取出最低位的值,即與1 相與即可實現目的,為0 則是偶數,為1 則是奇數。
- (x & 1) == 0,則x為偶數
- (x & 1) == 1,則x為奇數
// 判斷一個數是否為奇數
bool isOdd(int x) {return x & 1 == 1
}
位運算實踐快速冪
int power(int base, int exp) {int result = 1;while (exp > 0) {if (exp & 1) {result = (result * base) % MOD;}base = (base * base) % MOD;exp >>= 1;}return result;
}
?