Java int变量转换为byte导致的精度缺失

1.补码、反码和原码的概念

  • 原码:最高位是符号位,0代表为正数,1代表为负数,非符号位为该数字绝对值的二进制。
  • 反码:正数的反码和原码一致,负数的反码是对原码按位取反,只是最高位(符号位)不变。
  • 补码:正数的补码和原码一致,负数的补码是对原码按位取反(反码)加1,符号位不变。

注意:在计算机底层,都是以补码的形式进行存储的

数据类型 字节大小 多少位二进制 二进制位数含义(第一位从0开始)
int 4个字节 32位二进制 第0位到第30位是数字位,第31位是符号位
byte 1个字节 8位二进制 第0到第6位是数字位,第7位是符号位
类型 正数 负数
原码 将数字转换为二进制,就是原码 将对应的整数的符号位改为1即得到该负数的原码
反码 与原码一致 将对应的原码除符号位(最高位)外,其余为全部取反(0变1,1变0)
补码 与原码一致 将对应反码,在末尾加1,即得到补码
实例1
public static void main(String[] args){
		int intValue=522;//定义一个int
		byte byteValue=(byte)intValue;//int值类型转换为byte类型
		System.out.println(byteValue);
	}

最终打印出来为数字10。

接下来看下转换过程

一.int类型常量522的二进制:

第24位到第31位 第16位到第23位 第8位到第15位 第0位到第7位
0000000 0000000 00000100 00001010

二.int类型强制转换为byte类型,从32位变成8位(砍掉24位),则转换后二进制为:

第0位到第7位
00001010

因为最高位为0,所以为正数(正数的原码、反码和补码都是一致的),最终转换为十进制为10。

实例2
public static void main(String[] args){
		int intValue=129;//定义一个int
		byte byteValue=(byte)intValue;//int值类型转换为byte类型
		System.out.println(byteValue);
	}

最终打印出来为数字-127。

接下来看下转换过程

一.int类型常量129的二进制:

第24位到第31位 第16位到第23位 第8位到第15位 第0位到第7位
0000000 0000000 00000000 10000001

二.同上,int类型强制转换为byte类型,从32位变成8位(砍掉24位),则转换后二进制为:

第0位到第7位
10000001

上面提到过 在计算机底层,都是以补码的形式进行存储的

因为最高位为1,所以为负数,所以得到原码的话,需要反码-1,再进行数字位全部取反。

反码二进制为:

第0位到第7位
10000000

原码二进制为:

第0位到第7位
11111111

最终转换为十进制为-127。

-End


一.参考:黄金鸡米花博客

二.参考:周天详博客

你可能感兴趣的:(Java,java,开发语言)