位运算分为:与、或、异或、取反、左移、右移。左移和右移称为移位运算,移位运算分为算数移位和逻辑移位。
与、或、异或、取反
- 与:&
规则:同1为1,否则为0
- 或:|
规则:有1为1,否则为0
- 异或:⊕ 代码中为:^
规则:相同为0,不同为1
- 取反:~
移位运算
按照移位方向分为左移、右移;按照是否带符号分成算术移位和逻辑移位
左移一位:乘2
右移一位:除2
- 左移:<<
将全部二进制位向左移动若干位,高位丢弃,低位补0。
对于左移运算,算术移位和逻辑移位是相同的。
- 右移(向下取整):>>
将全部二进制位向右移动若干位,低位丢弃,高位的补位由算数移位或逻辑移位决定:
-
- 算数移位:高位补最高位(1)
- 逻辑移位:高位补0
1s和0s分别表示与x等长的一串1和一串0
获取某个位
将1左移i位,得到形如00010000的值。接着对这个值与num执行“位与”操作,从而将i位之外的所有位清零,最后检查结果是否为0。不为零则i位为1,为零则为0。
boolean getBit(int num,int i){
return ((num&(1 << i)) != 0);
}
设置某个位的值
先将1左移i位,得到形如00010000的值。接着对这个值和num执行“位或”操作,这样只会改变i位的值。
int setBit(int num,int i){
return num | (1 << i);
}
清零某个位的值
将1左移i位,得到形如00010000的值,对这个值取反进而得到类似11101111的值,接着对该值和num执行“位与”
int clearBit(int num,int i){
int mask = ~(1 << i);
return num & mask;
}
更新
用形如11101111的值将num的第i位清零。接着将待写入值v左移i位,得到一个i位为v但其余位都为0的数。最后,对之前的结果执行“位或”操作,v为1,则num的i位变为1
int updateBit(int num,int i,int v){
int mask = ~(1 << i);
return (num & mask) | (v << i);
}