剑指 Offer 15. 二进制中1的个数

剑指 Offer 15. 二进制中1的个数

这道题目是求整形数字的二进制中1的个数,并且符号位也计算在内,就是把数字作为无符号的整形处理。

这题有三种以上的做法,第一种是把每一位二进制上的数字与1做&运算后的结果加起来,将n右移一位,java的无符号的右移是>>>

代码如下:

public class Solution {
    // you need to treat n as an unsigned value
    public int hammingWeight(int n) {
        int res = 0;
        while (n!=0) {
            res += n&1;
            n>>>=1;
        }
        return res;
    }
}

第二种做法是n不断与(n-1)做&运算,这样就可以把n的最低一位1变为0,示例如下

n: 100100

n-1:100011

经过&运算之后,后三位就会全变为0

当不为0时,重复之前的做法并计数

代码:

public class Solution {
    // you need to treat n as an unsigned value
    public int hammingWeight(int n) {
        int res = 0;
        while (n!=0) {
            res++;
            n&=(n-1);
        }
        return res;
    }
}

第三种做法就是,n&(-n)可以取出n的最后一位1,例如二进制数1110010,经过运算可以得到最低位的1为10,让1110010减去10得1110000,不断把末尾1减去并计数即可得到结果

代码:

public class Solution {
    // you need to treat n as an unsigned value
    public int hammingWeight(int n) {
        int res = 0;
        while (n!=0) {
            res++;
            n-=n&(-n);
        }
        return res;
    }
}

8位有符号数的范围是-128~127

规定(维基百科-补码词条):

负数的补码 = 该负数的绝对值按位取反 + 1

则补码 1000 0000 ,减一得 0111 1111,按位取反即为128,即该补码对应的值为-128

总结:

  1. byte 占用一个字节, 8 位,对于计算机来说表数范围为 0000 0000 ~ 1111 1111
  2. 最高位表示符号位
  3. 计算机用补码表数
  4. 正数和0的补码 = 源码
  5. 负数的补码 = 该负数的绝对值按位取反 + 1
原文地址:https://www.cnblogs.com/xyqxyq/p/14409101.html