本文主要是介绍C++右移运算符的一个小坑及解决,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
《C++右移运算符的一个小坑及解决》文章指出右移运算符处理负数时左侧补1导致死循环,与除法行为不同,强调需注意补码机制以正确统计二进制1的个数...
我遇到了这么一个函数
template<typename T> unsigned char countByt(T byt) { unsigned char num=0; while(byt) { num += (byt & 0x01); byt >>= 1; // cout<<hex<<byt<<endl; } return num; }
很明显,这个函数是统计byt二进制下1的个数。
没毛病
但当我输入负数的时候,就会陷入死循环。
用那行注释中的东西输出中间过程:
由此可以看到
- 在python非负数下,右移运算符,左面补0.
- 在负数下,右移运算符,左面补1.
我对代码进行如下修改:
template<typename T> unsigned char countByt(T byt) { unsigned char num=0; while(byt) { num += (byt & 0x01); byt/=2; //byt >>= 1; //cout<<hex<<byt<<endl; } return num; }
负数的结果:
这个时候,统计的是其所对应正数的1的个数。
也很好理解
补码是其正数按位取反再加1
可以看到,一个数的正和负,它们最后一位一定是一样的!
1、如果我们用/=2来的话:
-1/2=0
那结果跟正数统计是一样的。
2、www.chinasem.cn如果我们用>>=1的话:
-1:ffffffff
右移一位后,由于左侧补1,
还是:ffffffff
死循环就发生了。
但我在实验的http://www.chinasem.cn时候又发现了有趣的一点:
int n; while(cin>>n) { cout<<(n>>1)<<endl; }
1 0 -1 -1 2 1 -2 -1 3 1 -3 -2 9 4 -9 -5 8 4 -8 -4
可以看到:>>=1 等价于除以2后的(向下)取整。
而 / 运算符,是先对正数部分取整,再加符号。
因此对两个int变量a,b:
a/b不一定小于 等于(double)a/b;
while(cin>>a>>b) cout<<((a/b)<=((double)a/b))<<endl;
输出:
5 XGcTVh3
1
-5 3
0
-5 -3
1
5 -3
0
总结
当使用右移运算符的时候,一定要注意输入为负数的可能!在负数下 >>1 和 /=2 并不等价!
这篇关于C++右移运算符的一个小坑及解决的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!