求二进制数中1的个数
原题是:“对于一个字节(8bit)的无符号整型变量,求其二进制表示中1的个数,要求算法的执行效率尽可能的高”
(1)第一种方法是通过对这个数字N求余数,如果求余后有余,那么表示当前位置有一个1,否则便没有。然后N=N/2
(2)第二种方法其实思想和第一种方法差不多,只不过N=N/2 改用移位来运算:N>>=1;然后用N 同1进行“与”运算,来判断末尾是否
为1,如果N的二进制形式末尾有1,则“与”结果为1,否则为0. 方法(1)和(2)的时间复杂度都为O(log2N),因为N是以2的指数速度递减的。
(3)第三种方式,比较巧妙。
(4)效率最高应该是第五种方法,呵呵,他比较变态的将“0-255”的每个数二进制形式的“1”的个数保存成了一个数组,然后直接返回个数,时间复杂度为O(1).
但是如果对于一个字节的无符号整形变量还好,只有256个数字,但是如果对于32位的整形,这明显就不可取了。
此题有一个扩展问题:“给定两个正整数(二进制形式表示)A和B,问把A变成B需要改变成多少位(bit)?也就是说,整数A和B的二进制表示中有多少位是不同的?”
要解此题,引入A和B的异或运算再合适不过了,如果对于两个操作数按位异或,可以使得两个操作数中相同的“位”置为0,不同的“位”置为1.
所以对于两个二进制如果异或,他们之间不相同的位置将会被标记出来(即置为1)。
如果10000111^01111000=11111111,表明这两个数字所有位置都不同。
所以此题又转化成了求多少个1?
代码如下(VC2005下测试通过):
int compareTwoNum(int aNum,int bNum){ int count =0; int num =aNum^bNum; while(num){ num&= (num-1); count++; } return count; }
作者:
Chris Wang
出处:
http://chriswang.cnblogs.com/
文章版权归本人所有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。