令人赞叹的位运算
时间:2022-07-23
本文章向大家介绍令人赞叹的位运算,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
想必大家每次阅读第三方源码时,都觉得其中的位运算很酷,让人神往又抓狂。为了搞懂那些操作的具体含义,想去深入了解那些魔法代码背后的原理。
之前我也写过一篇文章谈了一些面试中可能遇到的算法题,今天更多的是一些用法的总结。
我们先回顾下常见的位运算符:
- & 与运算 两个位都是 1 时,结果才为 1,否则为 0, 如 :1 0 0 1 1 & 1 1 0 0 1 =1 0 0 0 1
- |或运算 两个位都是 0 时,结果才为 0,否则为 1, 如 :1 0 0 1 1 | 1 1 0 0 1 =1 1 0 1 1
- ^ 异或运算,两个位相同则为 0,不同则为 1, 如 :1 0 0 1 1 ^ 1 1 0 0 1 =0 1 0 1 0
- ~ 取反运算,0 则变为 1,1 则变为 0, 如:~ 1 0 0 1 1 =0 1 1 0 0
然后我们再来看看一些常见的技巧。
一,我们知道我们的字符在计算机底层都是数字表示的,恰巧英文字符在ASCII 编码里通过位运算就能进行大小写转换。
- 利用或操作 | 和空格将英文字符转换为小写。
('a' | ' ') = 'a'
('A' | ' ') = 'a'
- 利用与操作 & 和下划线将英文字符转换为大写。
('b' & '') = 'B'` `('B' & '') = 'B'
- 利用异或操作 ^ 和空格进行英文字符大小写互换。
('d' ^ ' ') = 'D'
('D' ^ ' ') = 'd'
二,异或的性质非常方便
- 可以判断两个数是否异号:
int x = -1, y = 2; boolean f = ((x ^ y) < 0); // true
int x = 3, y = 2; boolean f = ((x ^ y) < 0); // false
- 也可以用来交换两个数:
int a = 1, b = 2;
a ^= b;
b ^= a;
a ^= b;
// 现在 a = 2, b = 1
三,判断奇偶数
- 只要根据数的最后一位是 0 还是 1 来决定即可,为 0 就是偶数,为 1 就是奇数。 ``` if(0 == (a & 1)) { //偶数 }
四,符号交换
* 交换符号将正数变成负数,负数变成正数。
int reversal(int a) { return ~a + 1; }
整数取反加1,正好变成其对应的负数(补码表示);负数取反加一,则变为其原码,即正数。
五,求绝对值
整数的绝对值是其本身,负数的绝对值正好可以对其进行取反加一求得,即我们首先判断其符号位(整数右移 31 位得到 ),然后根据符号进行相应的操作int
int abs(int a) { int i = a >> 31; return i == 0 ? a : (~a + 1); }
六,取反实现+1,-1(不过我感觉没啥用)
int n = 1; n = -~n; // 现在 n = 2
```
int n = 2;
n = ~-n;
// 现在 n = 1
七,位操作统计二进制中 1 的个数 统计二进制1的个数可以分别获取每个二进制位数,然后再统计其1的个数,此方法效率比较低。不过 n & (n - 1) 可以消除最后一个 1,所以可以用一个循环不停地消除 1 同时计数,直到 n 变成 0 为止。
while (n != 0) {
n = n & (n - 1);
res++;
}
怎么样,是不是感觉自己奇怪的知识又增加了??总体而言,虽然这些技巧有的提高了性能,有的简化了代码,但不是所有代码都那么好理解,大家还需要结合实际场景去理解这些技巧,从实际的题目中去找到它们的优势,它们的意义。happy coding~
- Js基础---红宝书读书日记(1)-------基本类型和引用类型
- 并发编程之future模式
- Html5模拟通讯录人员排序(sen.js)
- Goroutine + Channel 实践
- Http和Https的区别
- JavaScript实现单击全选 ,再次点击取消全选
- 连AI都在看《英雄联盟》游戏直播
- MAC使用adb工具
- 并发编程之master-worker模式
- Android WebView全面总结
- Url参数中出现+、空格、=、%、&、#等字符的解决办法
- 解决CSS垂直居中的几种方法(基于绝对定位,基于视口单位,Flexbox方法)
- Go语言学习之cgo(golang与C语言相互调用)
- golang之旅--数据类型之字符串
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- Yii2处理密码加密及验证的方法
- PHP实现获取ip地址的5种方法,以及插入用户登录日志操作示例
- python如何输出反斜杠
- 在Laravel5中正确设置文件权限的方法
- asp函数split()对应php函数explode()
- php获取目录下所有文件及目录(多种方法)(推荐)
- Python基于Twilio及腾讯云实现国际国内短信接口
- PHP __call()方法实现委托示例
- PHP中rename()函数的妙用讲解
- php使用mysqli和pdo扩展,测试对比mysql数据库的执行效率完整示例
- php实现小程序支付完整版
- Yii2框架视图(View)操作及Layout的使用方法分析
- php实现单笔转账到支付宝功能
- PHP使用Redis实现Session共享的实现示例
- windows10在visual studio2019下配置使用openCV4.3.0