第一种
在十进制中我们如果想得到某个数的每位数,可以循环对这个数进行(%10)和(/10)。
根据这个结论,我们可以知道,如果想得到一个数的每位2进制数,那就可以对这个数循环进行(%2)和(/2)。
int main()
{
unsigned int num = 0;
int count = 0;
scanf("%u", &num);
while (num)
{
if (num % 2 == 1)
count++;
num /= 2;
}
printf("%d", count);
return 0;
}
因为负数在内存中存储的方式和正数不一样,所以我们最好用无符号整形来接收和输入,这样一来负数也可以求了。
第二种
我们还可以用位移操作符来解题
int main()
{
int num = 0;
int count = 0;
scanf("%d", &num);
for (int i = 0; i < 32; i++)
{
if (((num >> i) & 1) == 1)
count++;
}
printf("%d", count);
return 0;
}
第三种
int main()
{
unsigned int num = 0;
int count = 0;
scanf("%u", &num);
while (num)
{
num &= (num - 1);
count++;
}
printf("%d", count);
return 0;
}
我们还能用第三种算法来判断一个数是不是2的n次方。
int main()
{
int num = 0;
scanf("%d", &num);
if ((num & (num - 1)) == 0)
printf("%d是2的n次方\n", num);
else
printf("%d不是2的n次方\n", num);
return 0;
}
当我们对一个2的n次方进行-1的时候,它的二进制会产生借位,就会导致原数的每一位和-1后的每一位都不一样,这时进行&运算就会得到0。