最容易想到方法的就是把二进制的每一位都拿出来与1进行比较,如果是1,就计数,这样就统计出来二进制序列中1的个数了。
完整代码:
<span style="font-size:14px;">#include<stdio.h>
int count_one_bits(unsigned value)
{
int count=0;
while(value)
{
if(value%2 == 1)
count++;
value/= 2;
}
return count;
}
int main()
{
unsigned int value;
int count=0;
{
printf(" 请输入一个数: ");
scanf(" %d ",&value);
count= count_one_bits(value);
printf(" count=%d\n ",count);
}
return 0;
}</span>
然而,这种方法只能解决无符号运算,如果一个数为负数,这个运算就会出现问题。因此,为了解决带符号运算数的问题,第二种方法就出现了。
完整代码:
<span style="font-size:14px;">#include<stdio.h>
int count_one_bits(int n)
{
int count = 0;
int i = 0;
for(i=0; i<32; i++)
{
if(n&1 == 1)
count++;
n>>1;
}
return count;
}
int main()
{
int num = -1;
int rem = count_one_bits(num);
printf(" %d\n ",rem);
return 0;
}</span>
说明:&:按位与运算符,先把十进制数换为二进制数在进行逐位比较。
规则:有0得0,否则为1。
所以上述代码中n&1结果取决于n,如果n为1,结果为1,如果n为0,结果为0,这样就实现了1的个数统计。
>>运算符:带符号右移运算符,将一个二进制位的操作数按指定移动的位数向右移位,移出位被丢弃,左边移出的空位一律补0或者符号位。
例如:11>>2
11的二进制为0000 0000 0000 0000 0000 0000 0000 1011
把低位的两个数字移出,该数为正数,最高位补0,所以结果为0000 0000 0000 0000 0000 0000 0000 0010(2)。
这种运算方法显然必须要循环32次,如果这个二进制数只有几个1呢,这样运算明显就明显降低了运算效率,因此,我试想,可不可以用更少的循环次数来实现呢,所以就出现了第三种方法。完整代码:
<span style="font-size:14px;">#include<stdio.h>
int count_one_bits(int n)
{
int count = 0;
while(n)
{
count++;
n=n&(n-1);
}
return count;
}
int main()
{
int num = -1;
int rem = count_one_bits(num);
printf(" %d\n ",rem);
return 0;
}
</span>