Java中的位运算

在阅读JDK源码的过程中,我们经常会看到类似>> << >>> | 这样的运算符,这在Java里面叫位运算符。

我们知道计算机是以二进制来表示数据的,也就是0和1。我们先简单介绍一下二进制是如何表示数据的。

原码、反码、补码和移码

(1)原码

在原码表示中,机器数的最高一位是符号位,0代表正号,1代表负号,余下各位是数的绝对值。

数值0的原码表示方法有两种: $[+0]_原$ = 0000 0000 , $[-0]_原$ = 1000 0000。

8位二进制数的取值范围是:[-127 , 127]

(2)反码

在反码表示中,机器数的最高一位是符号位,0代表正号,1代表负号。

正数的反码与原码相同;

负数的反码则是其绝对值按位求反。

数值0的反码表示方法有两种: $[-0]_反$ = 0000 0000 , $[-0]_反$ = 1111 1111。

(3)补码

在补码表示中,机器数的最高一位是符号位,0代表正号,1代表负号。

正数的补码与原码相同;

负数的补码则是其反码的末尾加1。

数值0的补码有唯一的表现形式,即 $[-0]_补$ = $[-0]_补$ = 0000 0000。

(4)移码

移码表示法是在数上增加一个偏移量来定义的,常用于表示浮点数中的阶码。对于定点整数,移。如果知道了一个数的补码,则将补码的最高位取反,即得到该数的移码。

位运算符

Java提供的位运算符有:左移( << )、右移( >> ) 、无符号右移( >>> ) 、位与( & ) 、位或( | )、位非( ~ )、位异或( ^ ),除了位非( ~ )是一元操作符外,其它的都是二元操作符。

1. 左移( << )

a << b 表示将数值 a 的二进制数值从 0 位算起到第 b - 1 位,整体向左方向移动 b 位,符号位不变,低位空出来的位补数值 0。

a << b = a * (2 ^ b)

2. 右移( >> )

a >> b 表示将数值 a 的二进制数值从 0 位算起到第 b - 1 位,整体向右方向移动 b 位,符号位不变,高位空出来的位补数值 0。

***a >> b = a / ( 2 ^ b )***

3. 无符号右移( >>> )

无符号右移运算符>>>和右移运算符>>是一样的,只不过右移时左边是补上符号位,而无符号右移运算符是补上0,也就是说,对于正数移位来说等同于:>>,负数通过此移位运算符能移位成正数。以-733183670>>>8为例来画一下图

4. 位与( & )

与运算时,进行运算的两个数,从最低位到最高位,一一对应。如果某 bit 的两个数值对应的值都是 1,则结果值相应的 bit 就是 1,否则为 0.

1
2
3
4
5
0 & 0 = 0,

0 & 1 = 0,

1 & 1 = 1

5. 位或( | )

与运算时,进行运算的两个数,从最低位到最高位,一一对应。如果某 bit 的两个数值对应的值只要 1 个为 1,则结果值相应的 bit 就是 1,否则为 0。

1
2
3
4
5
0 | 0 = 0,

0 | 1 = 1,

1 | 1 = 1

6. 位异或( ^ )

两个操作数进行异或时,对于同一位上,如果数值相同则为 0,数值不同则为 1。

1
2
3
4
5
1 ^ 0 = 1,

1 ^ 1 = 0,

0 ^ 0 = 0;

7. 位非( ~ )

对操作数的每一位进行操作,1 变成 0,0 变成 1。

updatedupdated2023-06-032023-06-03
加载评论