100分求解一道面试题那n&(n-1)

icerlion 2009-08-20 12:25:17
代码如下:


int Fun(int nValue)
{
int nCount = 0;
while (nValue)
{
nValue = nValue&(nValue-1);
++nCount;
}
return nCount;
}



求解Fun(9999);

代码运算结果为8,
为一道面试题,

下来想了半天不得其解,
请各位达人指点迷津。
...全文
376 点赞 收藏 14
写回复
14 条回复
切换为时间正序
请发表友善的回复…
发表回复
xhp7185 2010-08-12
高明啊!!
回复
PeacefulBY 2009-08-20
具体地说,如果nValue为奇数,则二进制形式为X...X1,nValue&(nValue-1)的结果为X...X0;
如果nValue为偶数,则二进制形式为X...X10...0,nValue&(nValue-1)的结果为X...X00...0;
相当于每次去掉末尾的1,这样就变成了统计1的个数,&是按位与运算
回复
PeacefulBY 2009-08-20
Fun就是用于计算nValue变换为二进制后1的个数
回复
arczee 2009-08-20
UP,学习了
貌似上面的位运算想了半天,终于有点明白了,大概是这样(以8bit为例):
使用0x55作位运算也就是将X的位两两累加,如 11 01 10 11 两两累中后 得到 10 01 01 10,
因为1+1=10 0+1=01 1+0=01 1+1=10 ,所以每二位一组标示X的二位的1的个数。
然后,以0x33对结果做位运算,为什么是0x33呢,因为结果是两位的,所以 是将其两位一组两两相加
得到 0011 0011 这一结果是四位一组的,每四位标示X的四位中的1的个数,
然后 再使用0x0f做位运算,可想而知,得到的是八位组标示的X的每八位中的1的个数。因为X只有八位,所以到此结束,结果为 0011+0011=0000 0110 ,即6个1
更多位数以此类推
回复
whg01 2009-08-20
《编程之美》中 “求二进制数中1的个数”,122页。
回复
currenttt 2009-08-20
帮顶,学习
回复
Paradin 2009-08-20
8l不明白
回复
hua_zhixing_ 2009-08-20
位运算用得少,半天没反应过来。
呵呵,学习了。
回复
绿色夹克衫 2009-08-20
每次去掉最后一个1,这样正好可以统计出1的个数。不过统计1的个数有log(n)的方法,最近并行计算比较热,位运算开始被特别重视起来。

贴一段网上的代码吧!

unsigned FindOneInNumber_03(unsigned int x)
{
const unsigned MASK1 = 0x55555555;
const unsigned MASK2 = 0x33333333;
const unsigned MASK4 = 0x0f0f0f0f;
const unsigned MASK8 = 0x00ff00ff;
const unsigned MASK16 = 0x0000ffff;

x = (x&MASK1 ) + (x>>1 &MASK1 );
x = (x&MASK2 ) + (x>>2 &MASK2 );
x = (x&MASK4 ) + (x>>4 &MASK4 );
x = (x&MASK8 ) + (x>>8 &MASK8 );
x = (x&MASK16) + (x>>16&MASK16);
return x;
}
回复
丈八涯 2009-08-20
[Quote=引用 1 楼 peacefulby 的回复:]
Fun就是用于计算nValue变换为二进制后1的个数
[/Quote]
正解.
回复
neohope 2009-08-20
恩,其实每次都是将二进制中最后一个1去掉,呵呵
回复
Paradin 2009-08-20
每次消掉最后一个1
回复
-空军- 2009-08-20
n为奇数(n的二进制表示的末位为1):
n: xxxxxxxx1
n-1: xxxxxxxx0
n&(n1-): xxxxxxxx0
相当于去掉最右边的一个1。

n为偶数且不等于0(n的二进制表示的末位为0):
n: xxxxx1000
n-1: xxxxx0111
n&(n1-): xxxxx0000
也是相当于去掉最右边的一个1。


所以,程序的效果就是统计传入的参数的二进制表示中1的个数。

如,9999 的二进制表示为: 0010 0111 0000 1111,共有8个1.
回复
hyram 2009-08-20
LS正解,见编程之美
回复
发动态
发帖子
数据结构与算法
创建于2007-08-27

3.2w+

社区成员

数据结构与算法相关内容讨论专区
申请成为版主
社区公告
暂无公告