第二章
- 关于关键字的注意
一、Java数据类型两大分支
Java的数据类型有两大分支
- 基本类型
在Java中表示一些简单的数据,以数值为主 - 引用类型
在Java中表示一些复杂的数据(对象)。
二、基本数据类型
1.六种数值相关
- 四种整数型
都表示一个整数,区别是底层所占用的内存大小,也决定了可以表示的数值范围的大小。
1)byte,字节型,1Byte=8Bits,
表示范围:-2^7 ~ 2^7-1,-128~127
2)short,短整型,2Byte=16Bits,
表示范围:-215~215-1,-32768~32767
3)int(最常⽤),整型,4Byte=32Bits,
表示范围:-231~231-1,-2147483648~2147483647
Java中整型的字面量常量默认是int类型
4)long,长整型,8Byte=64Bits
表示范围:-263~263-1
long类型整型字⾯量表示⽅法:数值后加l或L。
建议写⼤写的L,增强可读性。 - 两种浮点数
注意:浮点型⼀般不探讨最⼤最⼩值,⼀般探讨能够精确到⼩数点后的多少位。
float,单精度浮点型,4Bytes=32Bits
字⾯量在数值后边加f或F。
double,双精度浮点型,8Bytes=64Bits
字⾯量在数值后边加d或D。
注意:浮点型字⾯量默认类型是double。
2.一种字符相关
- char,2Byte=16Bits
本质是⼀个2字节构成的Unicode编码码值,在Java中⽤于表示单个字符,可以是⼀个阿拉伯数字、⼀个
中⽂汉字字符、⼀个英⽂字⺟、⼀个标点符号。
Unicode:万国码
⽆论字符数据在传输和存储时采⽤的是什么编码,只要进⼊到Java内存中,所有字符都是以Unicode形
式存在。
char的本质实际就是⼀个数值,代表某个Unicode编码表中码值的数值,⽽且是Java中唯⼀的⼀个⽆符
号数类型。
3.一种布尔类型
boolean,在Java中表示⼀种逻辑真或逻辑假,通常⽤于设置⼀些标志位、状态位,或者表示⼀个布尔表达式
的计算结果。
布尔表达式:逻辑判断
值只能有两种:true、false
在底层实际只需要⼀个bit就可以表示出两种状态,但是实际分配的时候会给它分配⼀个完整字节使⽤。
三、进制转换
1.二进制转十进制
【案例】
将⼆进制数01101101转换为⼗进制值.
- 方法一
- 方法二:用最接近该值的2的整n次幂剪掉对应数值得到
例如,将⼆进制数01101101转换为⼆进制,⽤01111111这个数值,将01101101下划线处两个0所在位置代表的
数值⼤⼩减掉即可。
思考:01111111和01101101的关系
01111111 = 64 + 32 + 16 + 8 + 4 + 2 + 1
01101101 = 64 + 32 + 0 + 8 + 4 + 0 + 1
通过观察可以得知,两式⼦差值为(16 + 2)。⽽16和2正好对应01101101这个数中右数第1位和第4位值为零的位
置。
⽽01111111属于较为规整的⼆进制值,很⽅便能⼝算出对应⼗进制值为127(2的7次为128,128-1=127),所
以01101101的值就是127-16-2=109。
2.十进制转二进制
⽅法⼀:除2取余法,参考标准化PDF⽂档
⽅法⼆:瞪眼法,⼝算进⾏拆分
⾸先了解前提,要知道任意⼗进制整数都可以由若⼲个2的整数次幂相加得来,例如:
19 = 16 + 2 + 1
37 = 32 + 4 + 1
88 = 64 + 16 + 8
……
所以,我们只需要将⼀个⼗进制数⼝算拆分为若⼲个2的整n次,再将每个n转化为⼆进制数对应位置的1拼写出来
即可。
四、关于数据类型的注意事项
- 8种基本数据类型变量的定义和赋值。
基本原则:最规范的写法等号左右两边的类型一致。
等号左边用于接收的变量数据类型和等号右边实际提供的数值类型是一致的。
byte、short类型
byte和short都没有专门的字面量表示方法。
所以Java中特殊规定,允许使用一个int类型字面量为byte或short变量赋值。
但是,编译器会对等号右边的常量值进行检查,如果超出等号左边类型实际
可表示的数值范围,就会编译报错。
也就是说,在给byte和short类型变量赋值的时候,
能成功的条件有两个:
1)等号右边一定是常量
2)常量的实际数值在byte/short可表示的范围内
- 整形的字面量默认为int类型。int最大值为21亿左右,如果超过则会编译出错。
- 如果要书写一个大于21亿大小的整形字面量,需要使用long类型的字面量:在数值后面加l/L.
- 注意:不能使用int变量为byte赋值,尽管int值可能确实在byte范围内
int i1 = 10;
byte b2 = i1; // 编译报错
- int类型使用能够被int兼容的变量或字面量类型赋值
例如:byte,short,char
int i='a';
- long类型使用能够被long兼容的变量或字面量类型赋值
long l= 'q';
long l =90;
- float类型,除了boolean,double其他的都兼容
特殊的:左边4Byte,右边8Byte
float f = 26265L;
- char类型
使用字符型字面量
char c1 = ‘a’;
使用一个int字面量为char赋值
编译器会检查实际数值大小是否在char可表示范围内
char c2 = 97;
单引号内书写Unicode编码形式
char c3 = ‘\u0061’;
使用int类型其他进制的字面量
char c4 = 0x0061;
五、类型转换
场景:使用等号进行赋值,左右两边类型不一致。
1.隐式类型转换(自动类型转换)
如果左边的类型能够兼容右边的类型,系统将自动进行隐式转换。
1)如果左右都是整型数,长度越大的,单位就越大
long > int > short > byte
2)如果两边都是浮点数,
左边是double、右边是float可以隐式提升
3)如果两边一边是整型一边是浮点型,
左边是浮点右边是整型,可以进行隐式提升
注意:浮点型总是要大于整型
4)涉及到char类型的转换
char是一个无符号数,所以它在和有符号数进行相互转换时,
不能单纯地看字节长度
4.1)左边char,右边byte,即便左大右小,但是也不能进行隐式转换
因为byte中存在char类型无法表示出的数值
4.2)一边是char,一边是short,两边等长
小结:char和(byte及short)之间都不能相互进行转换
4.3)右边是char,左边是int或比int更大的单位,
都可以进行隐式转换,例如:int、long、float、double
2、显示类型转换(强制类型转换)
在无法进行隐式转换的情况下强制完成而显示转换,转换完成可能有精度丢失。
强制转换一般发生在从大单位转小单位的场景中
大单位位数比较多,小单位位数比较小
从大到小强转的本质是舍掉多余的,表示不出来的二进制位
int --> byte 32bits --> 8bits
舍掉的高位中一定包含原本的符号位
剩余地位的首位就成了新的符号位,可能会对熟知的正负产生影响
补充:
1、Java中双目运算的规则
必须由两个相同类型操作数进行计算,
计算的结果也和操作数的类型是相同的。
int + int = int
float + float = float
2、不同单位的运算
如果两个操作数数据类型不一致,
那么会把较小的提升为和较大的相同的单位进行计算。
例如:int + float,会先把int值提升为float类型,
然后计算float + float,得到一个float结果。
3、byte和short的问题
byte和short这是出现在编译层面的两种类型,
但是在JVM中没有byte和short这么小的单位。
程序中所有byte和short值在参与计算的时候,
都会被JVM隐式提升为4Byte大小的int类型进行计算。
// byte和char相加
// byte先隐式提升为int,变成int+char
// 然后char隐式提升为int,变成int+int
byte b2 = -100;
char c = 'a';
System.out.println(b2 + c);
例子:
short s = 3;
s = s + 2;
//无法通过编译,int加short会变成int类型,不能赋值给short类型。
//不能将一个变量int和常量的值相加所得的int赋值给比int范围小的类型。
short s = 3 + 2;
//可以通过编译执行,右边的值虽然是int类型,但是是常量可以赋值给short
int i1 = 1;
int i2 = 2;
short s = i1 + i2;
//无法通过编译,不能将int类型的变量相加后赋值给short
位扩展问题:
位:二进制位
前提:
1)发生类型转换
2)由小单位向大单位转换
- 符号位扩展
如果由符号数进行扩展,前面补符号位 - 零扩展
如果是无符号数(char),前面无条件补0
例如:
System.out.println((int)(char)(byte)-1);
//输出65535
运算顺序:就近原则
第一步,int类型的-1强转为byte
第二步,byte强转为char
第三步,char强转int
1.int类型-1:32个1
补码:11111111 11111111 11111111 11111111
转为byte:
补码:11111111
源码:10000001
2.11111111强转为char类型
1)char底层本质就是一个数值
2)char是16位的类型,byte是8位
把有符号位byte强转为16位,需要进行符号位扩展
11111111 111111111
3.char转int
char无符号数,无法扩展符号位,需要给前面补零
(正数,补码和原码相同)00000000 00000000 111111111 11111111(int) 65535