这篇博客将详细介绍位逻辑运算符,并且有例题详解
目录
前言
这篇博客起源于我做一些关于c语言的oj题,发现角度新奇需要运用位操作,原来一直都没有真正会运用位操作,所以打算写一篇博客详细写下我对位操作的理解,最后会放上例题。
提示:以下是本篇文章正文内容,下面案例可供参考
一、位逻辑运算符
1.位逻辑运算符
位操作都是在二进制基础上进行操作,平时不加说明,直接声明定义的整型都为十进制。
如: int a=2;
2为二进制,要对它进行位操作时,先转换成二进制,
Tip: 整型为8个字节(byte),即32个比特位(bit)(一个二进制位即一个比特位)。
所以2的二进制位为:0000 0000 0000 0000 0000 0000 0000 0010
2.位逻辑运算符分类
符号 | 名称 | 介绍 |
& | 按位与 | 都为1,则为1 |
| | 按位或 | 有一个为1,则为1 |
^ | 按位异或 | 相同为0,相异为1 |
此处介绍会在下文详细解释。
二、按位与——' & '
1.解释
(1)两个二进制数低位对齐,对每一位依次比较,都为1则结果为1,否则为0。
(2) 对于位数不对齐的情况,采取在高位自动补0的操作。
如:
x | y | x&y |
0 | 0 | 0 |
1 | 1 | 1 |
1 | 0 | 0 |
0 | 1 | 0 |
2.用法介绍
根据&的特性,一个二进制数,&1为本身,&0可消除该位(把该位的二进制改成0)
如:假如一个二进制数为 111,要获取二进制位最低位只需使用&1的位操作
111
001 (位数不足高位补0)
结果为 001
三、按位或——' | '
1.解释
(1)两个二进制数低位对齐,对每一位依次比较,有一个为1则结果为1,都为0则为0。
(2) 对于位数不对齐的情况,采取在高位自动补0的操作。
如:
x | y | x&y |
0 | 0 | 0 |
1 | 1 | 1 |
1 | 0 | 1 |
0 | 1 | 1 |
2.用法介绍
根据特性,对某二进制数的某一位进行‘ | ’操作,|1结果为1,|0结果为本身。
四、按位异或——' ^ '
1.解释
(1)两个二进制数低位对齐,对每一位依次比较,相同为0,相异为1。
(2) 对于位数不对齐的情况,采取在高位自动补0的操作。
如:
x | y | x^y |
0 | 0 | 0 |
1 | 1 | 0 |
1 | 0 | 1 |
0 | 1 | 1 |
2.用法介绍
根据特性,一个数^本身,结果为0;^0结果为本身。
如:int n=10;
计算n^n和n^0。
10(整型32比特位)的二进制数为:00000000 00000000 00000000 00001010
0 (高位补0) 的二进制数为:00000000 00000000 00000000 00000000
10^10=(00000000 00000000 00000000 00000000)(二进制)=0(十进制)
10^ 0 =(00000000 00000000 00000000 00001010)(二进制)=10(十进制)
五、例题
1.例题的力扣🔗
建议没有写过的同学,先自己尝试一下。
2.只出现一次的数字
难度:简单
题目:
给你一个 非空 整数数组 nums ,除了某个元素只出现一次以外,其余每个元素均出现两次。找出那个只出现了一次的元素。
你必须设计并实现线性时间复杂度的算法来解决此问题,且该算法只使用常量额外空间。
示例 :
输入:nums = [2,2,1] 输出:1
考察知识点:
^按位异或操作,如题所示,除了某元素出现一次,其他元素均出现两次;
异或操作特性:^本身为0,^0为本身。
思路:
声明一个变量存放数组中元素累次按位异或的结果,出现两次的元素抵消成0,只剩下仅出现一次的元素,即这道题的结果。
代码:
class Solution {
public:
//找到只出现一次的数,其他数都出现两次
int singleNumber(vector<int>& nums) {
int ans=0;
for(int i=0;i<nums.size();i++)
{
ans^=nums[i];//异或运算的特点
//和0异或为本身
//和本身异或为0
}
return ans;
}
};
3.汉明距离
难度:简单
题目:
两个整数之间的汉明距离指的是这两个数字对应二进制位不同的位置的数目。
给你两个整数 x
和 y
,计算并返回它们之间的汉明距离。
示例 :
输入:x = 1, y = 4
输出:2
解释:
1 (0 0 0 1)
4 (0 1 0 0)
↑ ↑
上面的箭头指出了对应二进制位不同的位置。
考察知识点:
(1)异或操作
(2)按位与操作
(3)按位右移操作
思路:
将x和y进行按位异或操作,将结果储存在变量n中,再遍历n的二进制数的每一位,为1则代表对应二进制位不相同。
遍历操作并进行比较的操作的实现:将n&1,n的最后一位为1结果则为1,计数+1,再将n按位右移一位,将最后的左边一位挪到最后一位,则达到从最后一位开始遍历每一位的操作。
代码:
class Solution {
public:
int hammingDistance(int x, int y) {
int n=x^y;
int res=0;
while(n)
{
res+=( n & 1);
n>>=1;
}
return res;
}
};
例题总结
这两道题目的难度虽然不高,但也要求做题者牢牢理解位操作才能做出。
理解好每一个按位操作的特性,这种题目就能手拿把掐了。
总结
以上就是全部内容,这篇博客介绍了三个位操作的详细解释即例题,随着后面的学习,我会更新我的学习笔记。
感谢你看到这里,一起加油!