Java中的位运算,说实话,工作了两年的时间里,从来没有用过一次,因为平时都是些的是业务代码,很少接触比较底层的东西,我记得第一次在代码中看到还是在HashMap的Hash算法中看到的,这次重拾Java基础,着重理解了一下Java中的位运算,计算机中的运算一般都是操作反码进行运算,操作完成之后,再将结果的反码转化成原码,然后将二进制的结果转化成十进制输出出来,其实乘法和除法运算在计算机中都是通过位运算进行的,所以我觉得这部分应该好好整理一下,以下内容都是传智播客的Java基础中的讲解视频还有一些是讲解的课件、笔记中的内容,在此声明。
运算符
运算
位运算符的细节
<<
左移
空位补0,被移除的高位丢失
>>
右移
被移位的二进制最高位是0,右移后,空缺位补0,最高位是1,最高位补1
>>>
无符号右移
被移位二进制无论是0或者1,空缺位都是用0补
&
与运算
任何二进制位和0进行&运算,结果都是0,和1进行&运算,都是原值
|
或运算
任何二进制位和0进行|运算,结果都是原值,和1进行|运算,都是1
^
异或运算
任何相同二进制位进行^运算,结果都是0,不同二进制位进行^运算,结果都是1
~
反码
注意:
<
>>:右移稍微复杂一点,如果最高位是0,左边被移空的位就填入0,如果高位是1,左边被移空的位就填入1,相当于除以2的倍数
>>>:无论最高位是1还是0,左边被移空的高位都填入0
Java中运算符的优先级:(图片来源网路)
代码演示各种位运算:
1 /*
2 要做位运算,首先要把数据转换为二进制。3 */
4 public static voidmain(String[] args) {5 //&,|,^,~
6 int a = 3;7 int b = 4;8
9 System.out.println(3 & 4);10 System.out.println(3 | 4);11 System.out.println(3 ^ 4);12 System.out.println(~3);13
14 }
代码分析解读:
分析:因为是位运算,所以我们必须先把数据换算成二进制。
3的二进制:11
00000000 00000000 00000000 00000011
4的二进制:100
00000000 00000000 00000000 00000100
&位与运算:有0则0。
00000000 00000000 00000000 00000011
&00000000 00000000 00000000 00000100
-----------------------------------
00000000 00000000 00000000 00000000
结果是:0
|位或运算:有1则1。
00000000 00000000 00000000 00000011
|00000000 00000000 00000000 00000100
-----------------------------------
00000000 00000000 00000000 00000111
结果是:7
^位异或运算:相同则0,不同则1。
00000000 00000000 00000000 00000011
&00000000 00000000 00000000 00000100
-----------------------------------
00000000 00000000 00000000 00000111
结果是:7
~按位取反运算符:0变1,1变0
00000000 00000000 00000000 00000011
~11111111 11111111 11111111 11111100 (补码)
补码:11111111 11111111 11111111 11111100
反码:11111111 11111111 11111111 11111011
原码:10000000 00000000 00000000 00000100
结果是:-4
^异或运算的特点:
1 /*
2 ^的特点:一个数据对另一个数据位异或两次,该数本身不变。3 */
4 public static voidmain(String[] args) {5 int a = 10;6 int b = 20;7
8 System.out.println(a ^ b ^ b); //10
9 System.out.println(a ^ b ^ a); //20
10 }
1 /*
2 <<:>>:右移 最高位是0,左边补齐0;最高为是1,左边补齐14 >>>:无符号右移 无论最高位是0还是1,左边补齐05
6 面试题:7 请用最有效率的方式写出计算2乘以8的结果?8 2 * 89 2 << 310 */
11 public static voidmain(String[] args) {12 //<< 把<
13 System.out.println(3 << 2); //3*2^2 = 3*4 = 12;14
15 //>> 把>>左边的数据除以2的移动次幂
16 System.out.println(24 >> 2); //24 / 2^2 = 24 / 4 = 6
17 System.out.println(24 >>> 2);18
19 System.out.println(-24 >> 2);20 System.out.println(-24 >>> 2);21 }
代码分析解读(32位):
计算出3的二进制:11
00000000 00000000 00000000 00000011
(00)000000 00000000 00000000 0000001100
>>(右移)的移动:
计算出-24的二进制:11000
原码:10000000 00000000 00000000 00011000
反码:11111111 11111111 11111111 11100111
补码:11111111 11111111 11111111 11101000
11111111 11111111 11111111 11101000
1111111111 11111111 11111111 111010(00) 补码
补码:1111111111 11111111 11111111 111010
反码:1111111111 11111111 11111111 111001
原码:1000000000 00000000 00000000 000110
结果:-6
>>>(无符号右移)的移动:
计算出-24的二进制:11000
原码:10000000 00000000 00000000 00011000
反码:11111111 11111111 11111111 11100111
补码:11111111 11111111 11111111 11101000
11111111 11111111 11111111 11101000
0011111111 11111111 11111111 111010(00)
结果:1073741818