简单了解python的一些位运算技巧


Posted in Python onJuly 13, 2019

前言

位运算的性能大家想必是清楚的,效率绝对高。相信爱好源码的同学,在学习阅读源码的过程中会发现不少源码使用了位运算。但是为啥在实际编程过程中应用少呢?想必最大的原因,是较为难懂。不过,在面试的过程中,在手写代码过程中,写出一两个位运算的代码,还会让面试官眼前一亮的。

位运算常用的运算符包括&(按位与), | (按位或),~(按位非),^(按位异或),<< (有符号左移位) ,>>(有符号右移位)。

简单了解python的一些位运算技巧

下面用几个例子说明其应用,希望对你有所启发。

1、判断奇数还是偶数

通常判断奇数还是偶数我们想到的办法就是除以2,看余数是否为0。

Python代码如下:

def isodd(x):
 return True if (x % 2 <> 0) else False

如何使用位运算呢?

我们只需要使用&运算,与1进行&,如果为1,那么该数为奇数;如果为0,那么该数是偶数,Python代码如下:

def isodd(x):
 return True if (x & 1) else False

2、左移一位相当于乘以2,右移一位相当于除以2

在面试的过程中,通常会遇到的一个问题是写二分查找代码。

二分查找的代码如下:

def binary_search(list, item):
 '''
 :param list: 有序列表
 :param item: 要查找的元素
 :return: item在list中的索引,若不在list中返回None
 '''
 low = 0
 high = len(list) - 1
 while low <= high:
 midpoint = (low + high) // 2
 if list[midpoint] == item:
 return midpoint
 elif list[midpoint] < item:
 low = midpoint + 1
 elif list[midpoint] > item:
 high = midpoint - 1
 return None

其中有一步是需要取最小小标和最大下标的中间值,若使用位运算符,midpoint = (low + high) >> 1,面试官肯定会对你刮目相看。

3、交换两个数值

数值交换的代码相信大家都非常熟悉了,因为似乎是从学编程语言的最开始就一直用:

temp = b
b = a
a = temp

但是怎么使用位运算来完成此功能呢?

a ^= b
b ^= a
a ^= b

确实比较难理解,原理是什么呢?

第一行,a = a ^ b,很容易理解;

第二行, b = b ^ a = b ^ a ^ b,由于 b ^ b = 0,所以 b = a ^ 0,即 b = a;

第三行, a = a ^ b ,由于a在第一步重新赋值,所以,a = a ^ b ^ a = b,完成了数值交换。

这里,总结下异或运算的特性:任意数和自身异或结果为0;0和任意数异或结果还是其本身。

4、寻找数据列表中的独一无二

有一个数据列表(2N+1个整数),只有一个数出现了1次,其余N个数都出现了2次。如何找到这个独一无二的数据?

看到这个题目,相信大家第一次想到的算法肯定是计数,建立列表,循环整个数据并计数,然后遍历这个列表找到出现次数为1的数据。

这样,空间复杂度为O(N)。

如何降低空间复杂度呢?

注意看一下刚刚讲过的异或的特性:任意数和自身异或结果为0;0和任意数异或结果还是其本身。

那么,出现了2次的N个数异或的结果是0,再与出现次数为1次的数异或的结果即为该数。即:找到这个独一无二数据的办法是通过对全部的数据进行异或操作,空间复杂度降低为O(1)。

5、计算一个数值的二进制数中有多少个1

相信有了之前的基础,大家很容易实现这个算法。单纯的通过位运算,与1进行与运算,看是否结果为1,然后右移1位,继续判断。Python代码实现如下:

def number1Bit(x):
 count = 0
 while x:
 count = count + (x&1)
 x = x >> 1
 return count

这样存在一个问题,就是如果有连续多个0,那么需要做多次移位操作。有没有简单的方式跳过连续多个0的情况?

那就是通过与(x-1)进行&运算。这里可能不太好理解,举例说明一下

x 1110 0000
x - 1 1101 1111
x&(x-1) 1100 0000

通过这种方式,会把最后的那个1检测出来。

Python代码实现如下:

def number1Bit(x):
 count = 0
 while x:
 count = count + 1
 x = x & (x-1)
 return count

总结:

1、与运算通常应用的场景是获取某一位的值为1还是0(如判断奇数偶数,统计数值中1的个数);

2、左移右移特性:左移一位相当于乘以2,右移一位相当于除以2;

3、异或特性:任意数和自身异或结果为0;0和任意数异或结果还是其本身。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python进阶教程之循环对象
Aug 30 Python
10款最好的Web开发的 Python 框架
Mar 18 Python
栈和队列数据结构的基本概念及其相关的Python实现
Aug 24 Python
用pandas按列合并两个文件的实例
Apr 12 Python
Python wxPython库消息对话框MessageDialog用法示例
Sep 03 Python
很酷的python表白工具 你喜欢我吗
Apr 11 Python
使用python绘制二维图形示例
Nov 22 Python
python3实现绘制二维点图
Dec 04 Python
python爬取本站电子书信息并入库的实现代码
Jan 20 Python
python列表切片和嵌套列表取值操作详解
Feb 27 Python
python MultipartEncoder传输zip文件实例
Apr 07 Python
详细介绍python操作RabbitMq
Apr 12 Python
简单了解python PEP的一些知识
Jul 13 #Python
python爬虫神器Pyppeteer入门及使用
Jul 13 #Python
Python 分享10个PyCharm技巧
Jul 13 #Python
简单了解Python3里的一些新特性
Jul 13 #Python
python将类似json的数据存储到MySQL中的实例
Jul 12 #Python
Django对数据库进行添加与更新的例子
Jul 12 #Python
Python 绘制酷炫的三维图步骤详解
Jul 12 #Python
You might like
smarty的保留变量问题
2008/10/23 PHP
PHP性能优化准备篇图解PEAR安装
2011/12/05 PHP
php实现的Timer页面运行时间监测类
2014/09/24 PHP
PHP字符串比较函数strcmp()和strcasecmp()使用总结
2014/11/19 PHP
php简单备份与还原MySql的方法
2016/05/09 PHP
PHP实现单例模式建立数据库连接的方法分析
2020/02/11 PHP
JavaScript延迟加载
2021/03/09 Javascript
js数组的操作详解
2013/03/27 Javascript
基于JQuery 选择器使用说明介绍
2013/04/18 Javascript
Javascript中常见的校验如域名、手机、邮箱等等
2014/01/02 Javascript
JS动态增加删除UL节点LI及相关内容示例
2014/05/21 Javascript
JavaScript学习笔记之Cookie对象
2015/01/22 Javascript
简单实现js选项卡切换效果
2016/02/03 Javascript
12个非常有用的JavaScript技巧
2017/05/17 Javascript
JS作用域链详解
2017/06/26 Javascript
JS获取字符对应的ASCII码实例
2017/09/10 Javascript
详解Vue项目编译后部署在非网站根目录的解决方案
2018/04/26 Javascript
解决layui中table异步数据请求不支持自定义返回数据格式的问题
2018/08/19 Javascript
Vue的watch和computed方法的使用及区别介绍
2018/09/06 Javascript
[02:41]辉夜杯现场一家三口 “我爸玩风行 我玩血魔”
2015/12/27 DOTA
[49:43]VG vs FNATIC 2019国际邀请赛小组赛 BO2 第一场 8.15
2019/08/17 DOTA
[01:04:02]DOTA2-DPC中国联赛 正赛 Elephant vs IG BO3 第二场 1月24日
2021/03/11 DOTA
Python快速查找list中相同部分的方法
2018/06/27 Python
python 移除字符串尾部的数字方法
2018/07/17 Python
pytorch如何冻结某层参数的实现
2020/01/10 Python
python 实现性别识别
2020/11/21 Python
伦敦眼门票在线预订:London Eye
2018/05/31 全球购物
英国卫浴商店:Ergonomic Design
2019/09/22 全球购物
俄罗斯品牌服装和鞋子在线商店:BRIONITY
2020/03/26 全球购物
如何用SQL语句进行模糊查找
2015/09/25 面试题
机械操作工岗位职责
2014/08/08 职场文书
联谊活动总结
2014/08/28 职场文书
违反单位工作制度检讨书
2014/10/25 职场文书
2015年社区综治宣传月活动总结
2015/03/25 职场文书
承诺书模板大全
2015/05/04 职场文书
在redisCluster中模糊获取key方式
2021/07/09 Redis