(1):按位运算符&:例如:0 & 0 = 0, 0 & 1 = 0, 1 & 0 = 0, 1 & 1 = 1 即同为 1 的位,结果为 1,否则结果为 0。
(2)按位或运算符|:例如:0 | 0 = 0, 0 | 1 = 1, 1 | 0 = 1, 1 | 1 = 1即只要有1个是1的位,结果为1,否则为0。
(3)按位异或运算符^:例如:0 ^ 0 = 0, 0 ^ 1 = 1, 1 ^ 0 = 1, 1 ^ 1 = 0 即相应位的值相同的,结果为 0,不相同的结果为 1。
(4)按位取反运算符~:用来求一个位串信息按位的反,即哪些为0的位,结果是1,而哪些为1的位,结果是0。
(4)左移运算符:
规则:按二进制形式把所有的数字向左移动对应的位数,高位移出(舍弃),低位的空位补零(左移一位相当于乘2)。
计算方法:例如:8 << n的值为8*(2^n)
(5)右移运算符:
规则:按二进制形式把所有的数字向右移动对应的位数,低位移出(舍弃),高位的空位补符号位,即正数补零,负数补1(右移一位相当于除2)。
计算方法:例如:8 >> n的值为 8/(2^n) ,这里是取商哈,不要余数。
巧用:
可利用右移运算符计算a的第b个二进制位是什么:(a>>b)&1。
二进制枚举子集:
#include<stdio.h> int k[5] = {1,2,3,4,5}; //二进制枚举子集:n个数有2^n个子集,对应一共有2^n个二进制数。 //每个二进制数的位权(0||1)对应原集合中的数是否存在于该子集 ,0为不存在,1为存在 void print(int s,int n) { int i; for(i = 0; i < s; i ++) if(s&(1<<i)) printf("%d ",k[i]); //比如s = 7 ->二进制数为:00111 //当i = 0,1,2时才输出s=7中的数 //s&(1<<0) == 7&1 == 00111&1 == 1 输出 k[0]=1 //s&(1<<1) == 7&2 == 00111&10 == 1 输出 k[1]=2 //s&(1<<2) == 7&4 == 00111&100 == 1输出 k[2] = 3 printf(" "); return; } int main() { int i,n = 5; for(i = 0; i < (1<<n); i ++)//(1<<n)等价于1*2^n { print(i,n); } return 0; }
参考资料:
https://baike.baidu.com/item/%E8%BF%90%E7%AE%97%E7%AC%A6/7752795
http://blog.sina.com.cn/s/blog_4e345ce70100u5pr.html
http://blog.csdn.net/liangzhaoyang1/article/details/52853207