Java中区分>>,<<,>>>
前言
首先需要知道在Java基本数据类型中不存在无符号数,即全为有符号数,>>,<<,>>>分别表示算术右移,算术左移,逻辑右移(无符号右移)
对于了解原码,反码,补码的读者可以直接跳过“有符号数的表示”部分
有符号数的表示(补充了解)
1.原码
最左边一位二进制表示这个数的符号: ”0“代表正,”1“代表负。后面是它的”有效数字“。
一个字节存储的有符号数原码,有127个正数;有127个负数和2个”0“。
‘正’0:0 000 0000;‘负’0:1 000 0000;
2. 反码
用最高位‘0’表示符号为正,‘1’表示符号为负。符号位之后的二进制位用来存储这个数的有效数字:正数的有效数字不变,负数的有效数字取反。
1字节存储有符号数反码,有127个正数,127个负数和2个“0”,
“正”0:0 000 0000, “负”0:1 111 1111.
3. 补码
补码表示法仍然用最高有效位(MSB)表示一个有符号数的符号,“1”表示符号为负,“0”表示符号为正。
其他二进制位数用来存储这个数的有效数字。正数的有效数字不变,负数的有效数字取反后最低位加1.
算术右移,算术左移,逻辑右移
1. 总述
>> : 算术右移,num >> 1,低位溢出,高位补符号位,在十进制数值上相当于num除以2
<< : 算术左移,num << 1,高位溢出,低位补0,在十进制数值上相当于num乘以2
>>> : 逻辑右移,忽略符号位,空位都以0补齐
2.逻辑右移详解
我们知道在Java中Integer占用4个字节,32位,最高位为符号位。Java中的数值用补码表示。
正数
根据上节知识可知,正数的补码等于原码,此处以10为例。
10在Java中的二进制表示为:0000 0000 0000 1010
现在进行逻辑右移: 10>>>2
逻辑右移后的二进制表示为: 00 0000 0000 0010 (未补齐)
逻辑右移后的二进制表示为: 0000 0000 0000 0010 (0补齐)
负数
此处以-10为例。
-10在java中的二进制表示为:1111 1111 1111 0110
现在进行逻辑右移:-10>>>2
逻辑右移后的二进制表示为: 11 1111 1111 1101 (未补齐)
逻辑右移后的二进制表示为: 0011 1111 1111 1101 (0补齐)
测试代码
package test;
public class test {
public static void main(String[] args){
int num = -10;
//本身二进制结果
printInfo(num);
//右移2位后二进制结果
printInfo(num>>2);
System.out.println(num>>2);
//左移1位后二进制结果
printInfo(num<<2);
System.out.println(num<<2);
//逻辑右移(无符号右移)1位后二进制结果
printInfo(num>>>2);
System.out.println(num>>>2);
}
//转二进制
private static void printInfo(int num){
System.out.println(Integer.toBinaryString(num));
}
}
读者可以自行修改测试。
写在最后
实际举例进行分析,并结合代码实践,才能彻底理解,算术和逻辑的区别,建议读者反复阅读几遍。
本人新手,如果有问题欢迎大佬们评论指出。