位运算小结

位操作基础

位运算小结_第1张图片
位运算符
  1. Java还有一个无符号右移运算符>>>,强行右移,左侧补零。以及还有相应的复合运算符。
  2. 位操作只能用于整形数据,对 float 和 double 类型进行位操作会被编译器报错。
  3. 注意位运算的优先级较低,比+-*/还要低,记得加括号。

位运算应用

交换两个数

主要用到异或运算的性质,异或还有其他用途。
x^ y ^y=x;
x^0=x;
x^x=0;

public  class Temp{
    public static void main(String[] args){
        int a=2,b=12;
        a ^= b;
        b ^= a;
        a ^= b;
        System.out.println("a:"+a);
        System.out.println("b:"+b);
    }
}

另一种交换方法

public class Temp {
    public static void main(String[] args) {
        int a = 2, b = 3;
        a = a + b;
        b = a - b;
        a = a - b;
        System.out.println(a);
        System.out.println(b);
    }
}

判断奇偶性

奇数二进制最后一位是1,偶数为零。

public class Temp {
    public static void main(String[] args) {
        int a = 2, b = 3;
        System.out.println("2是奇数?" + ((a & 1) == 1));
        System.out.println("3是奇数?" + ((b & 1) == 1));
    }
}

与2的次方相乘相除

public class Temp {
    public static void main(String[] args) {
        int a = 16;
        System.out.println(a >> 1); // devide by 2^1
        System.out.println(a << 1); // mutiple by 2^1
        System.out.println(a >> 3); // devide by 2^3
    }
}

判断某个数是否是2的次方

如果某个数是2的次方,则这个数的二进制形式‘1’的个数为1,即1,10,100,1000等形式。

public class Temp {
    public static void main(String[] args) {
        int a = 16, b = 15;
        // use n&(n-1)==0&n>0
        System.out.println(a > 0 && (a & (a - 1)) == 0);
        System.out.println(b > 0 && (b & (b - 1)) == 0);
    }
}

或者使用数学方法

public class Temp {
    public static void main(String[] args) {
        int a = 16, b = 15;
        System.out.println((int) (Math.pow(2, 30)) % a == 0);
        System.out.println((int) (Math.pow(2, 30)) % b == 0);
    }
}

数学方法可以推广到3的次方,4的次方,数学定理

2^m 可以整除2^n (m>n)

变换符号

整数变负数,负数变正数,即求反再加一

public class Temp {
    public static void main(String[] args) {
        int a = 16, b = -15;
        System.out.println(~a+1);
        System.out.println(~b+1);
    }
}

求绝对值

  1. 先移位来取符号位,int i = a >> 31; 要注意如果 a 为正数,i 等于 0,为负数,i 等于 -1。然后对i进行判断——如果i等于0,直接返回。否之,返回~a+1。
public class Temp {
    public static void main(String[] args) {
        int a = 16, b = -15;
        System.out.println((a >> 31) == 0 ? a : ~a + 1);
        System.out.println(b >> 31 == 0 ? b : ~b + 1);
    }
}
  1. 对于任何数,与 0 异或都会保持不变,与 -1 即 0xFFFFFFFF 异或就相当于取反(注意,计算机表示使用补码表示)。因此,a 与 i 异或后再减 i(因为 i 为 0 或 -1,所以减 i即是要么加 0要么加 1)也可以得到绝对值。所以可以对上面代码优化下:
public class Temp {
    public static void main(String[] args) {
        int a = 16, b = -15;
        int i = a >> 31;
        System.out.println((a ^ i) - i);
        int j = b >> 31;
        System.out.println((b ^ j) - j);
    }
}

leetcodeBIT相关题目bit manipulation

你可能感兴趣的:(位运算小结)