算法打卡day11-二进制中1的个数

138 阅读1分钟

描述

输入一个整数 n ,输出该数32位二进制表示中1的个数。其中负数用补码表示。

数据范围:−231<=�<=231−1−231<=n<=231−1

即范围为:−2147483648<=�<=2147483647−2147483648<=n<=2147483647

示例1

输入:

10

复制

返回值:

2

复制

说明:

十进制中10的32位二进制表示为0000 0000 0000 0000 0000 0000 0000 1010,其中有两个1。       

示例2

输入:

-1

返回值:

32

说明:

负数使用补码表示 ,-1的32位二进制表示为1111 1111 1111 1111 1111 1111 1111 1111,其中32个1    

解法:

int NumberOf1(int n ) {
    // write code here
    int sum = 0,
        m;  //sum用于记录1的个数,m用于记录正数情况下取余的结果
    if (n > 0) {       //正数比较简单,直接转换二进制数个数即可
        while (1) {
            m = n % 2;
            if (m == 1) sum++;
            n = n / 2;
            if (n == 0) break;
        }
        return sum;
    }
    if (n < 0) {                  //原始方法求补码
        n = -1 * n;               //先变成正数
        int a[32];
        for (int i = 31; i >= 0; i--) {  //用a数组记录n的正数的二进制数
            a[i] = n % 2;
            n = n / 2;
        }
        a[0] = 1;                       //符号位取反
        for (int i = 1; i <= 31; i++) {  //除符号位外各位0变1,1变0
            if (a[i] == 0) {
                a[i] = 1;
                continue;
            } else {
                a[i] = 0;
                continue;
            }
        }
        a[31] = a[31] + 1;             //整体+1
        for (int i = 31; i > 0; i--) {      //考虑+1后的进位问题
            if (a[i] == 2) a[i - 1] = a[i - 1] + 1;
        }
        if (a[0] == 2) a[0] =
                1; //高位产生溢出时,符号位为1不变,应对-2147483648
        for (int i = 0; i < 32; i++) { //求1的个数
            if (a[i] == 1) sum++;
        }
        return sum;
    }
    return 0;
}