zoukankan      html  css  js  c++  java
  • 剑指Offer:二进制中1的个数

    题目:输入一个整数,输出该数二进制表示中1的个数。

    // 二进制中1的个数
    
    #include <stdio.h>
    
    int wrong_count_1_bits(int n) // 错误解法: 当n为负数时, n>>=1右移, 最高位补1, 陷入死循环
    {
        int count = 0;
        while(n)
        {
            if( n & 1 )
                ++count;
            n >>= 1;
        }
        return count;
    }
    
    int count_1_bits(int n) // 常规解法, 若sizeof(int)=4, 循环32次
    {
        unsigned int mask = 1;
        int count = 0;
        while(mask) // 循环32次后, mask变为0
        {
            if( mask & n )
                ++count;
            mask <<= 1;
        }
        return count;
    }
    
    int perfect_count_1_bits(int n) // 高效解法, 若n含二进制位为1的位数为t, 则循环t次
    {
        int count = 0;
        while(n)
        {
            n = (n-1) & n; // 执行该语句后, n的二进制表示中, 最右边的1被置为0, 其余各位不变, 也即是每循环一次, 消去n最靠右的1
            ++count;
        }
        return count;
    }
    
    int static_table_count_1_bits(int n) // 静态表法
    {
        int table[16] =
        {
            0, 1, 1, 2,
            1, 2, 2, 3,
            1, 2, 2, 3,
            2, 3, 3, 4
        };
    
        int count =0 ;
        while (n)
        {
            count += table[n &0xf] ;
            n >>=4 ;
        }
        return count ;
    }
    
    int main(void)
    {
        printf("sizeof(int)=%d
    ",sizeof(int));
        printf("%d
    ",0x0fffff73); // 非负数正常; 负数(如0xffffff73)会导致程序在wrong_count_1_bits函数处陷入死循环
        int count1 = count_1_bits(0x0fffff73);
        int count2 = perfect_count_1_bits(0x0fffff73);
        int count3 = wrong_count_1_bits(0x0fffff73);
        int count4 = static_table_count_1_bits(0x0fffff73);
        printf("count1=%d,count2=%d,count3=%d,count4=%d
    ",count1,count2,count3,count4);
    
        return 0;
    }

    关键点:把一个整数减去1之后再和原来的整数做按位与运算& ,得到的结果相当于把整数的二进制表示中的最右边一个1变成0。

    相关题目1:用一条语句判断一个整数是不是2的整数次方

    if( (n-1)&n == 0 ) printf("Yes ");

    相关题目2:输入两个整数m和n,计算需要改变m的二进制表示中的多少位才能得到n。

    步骤1:求这两个数的异或 t = m^n;

    步骤2:统计异或结果t的二进制表示中1的个数,即为需要改变的位数。

    相关题目3:二进制中0的个数

    方法1:上面常规解法中,改成 if( n^mask == 1 )  ++count;

    方法2:先使用上面某种方法求得“二进制中1的个数”,间接求解:sizeof(int)*8 - 1的个数

  • 相关阅读:
    JAVA多态
    JAVA中的继承
    Nginx配置中root和alisa指定文件路径的区别
    NGINX配置详解
    Jenkins填坑之邮件模板分享
    jenkins填坑之HTML报告样式问题
    Jenkins填坑之仅获取本次构建的HTML报告作为附件发送邮件
    Jenkins填坑之发送邮件无法获取HTML报告作为附件
    jenkins填坑之邮件模板中的变量无法正常获取值
    Jenkins填坑之构建ant项目时,执行结果提示input file xxx.jtl does not exist
  • 原文地址:https://www.cnblogs.com/DayByDay/p/3866371.html
Copyright © 2011-2022 走看看