基本数据类型
Java 中有 8 种基本数据类型,主要为:
- 6 种数字类型:
- 4 种整型:
byte
、short
、int
、long
- 2 种浮点型:
float
、double
- 4 种整型:
- 1 种字符类型:
char
- 1 种布尔型:
boolean
8 种基本数据类型的默认值和占用空间大小为:1
2
3
4
5
6
7
8
9
10
11
12
13/**
* byte: -128 ~ 127
* short: -32768 ~ 32767
* int: -2147483648 ~ 2147483647
* long: -9223372036854775808 ~ 9223372036854775807
*
* float: 1.4e-45 ~ 3.4028235e38
* double: 4.9e-324 ~ 1.7976931348623157e308
*
* char: 0 ~ 65535
*
* boolean: ture or false
*/
基本类型 | 位数 | 字节 | 默认值 |
---|---|---|---|
byte | 8 | 1 | 0 |
short | 16 | 2 | 0 |
int | 32 | 4 | 0 |
long | 64 | 8 | 0L |
char | 16 | 2 | ‘u0000’ |
float | 32 | 4 | 0f |
double | 64 | 8 | 0d |
boolean | 1 | false |
对于 boolean,官方文档未明确定义,它依赖于 JVM 厂商的具体实现。逻辑上理解是占用 1 位,但是实际中会考虑计算机高效存储因素。
包装类
8 种基本数据类型所对应的包装类分别为:Byte
、Short
、Integer
、Long
、Float
、Double
、Character
、Boolean
。
包装类的缓存机制
- Java 中的包装类使用缓存机制提升性能,如果创建数的大小超过了缓存的对应范围就会创建新的对象。
- 本质上,缓存机制是在性能和资源之间的权衡。
整型
Byte
、Short
、Integer
、Long
四种包装类默认创建 -128 ~ 127 的相应类型的缓存数据。
以Integer
为例:
1 | /** |
所有整型包装类对象值的比较,全部使用equals()
进行比较。
1 | Integer i1 = 143; |
在 -128 ~ 127 之间赋值的Integer
对象是在IntegerCache.cache
产生,会复用已有对象,这个区间内的Integer
值可以直接使用==
进行判断。但是这个区间之外的所有数据或者Integer
对象,都会在堆上产生,并不会复用已有对象,这是一个大坑,推荐使用equals()
进行判断。
字符型
Character
创建了 0 ~ 127 范围的缓存数据。
1 | /** |
布尔型
Boolean
直接返回True
或False
。
1 | /** |
浮点型
特别地,Java 中的Float
、Double
没有实现缓存机制。
和基本数据类型的区别
- 包装类型可以用于泛型,基本类型不可以。
- 相比对象类型,基本数据类型占用的空间非常小。
- 不赋值的情况下,包装类型默认为 null,基本类型有默认值不为 null。
- 基本数据类型的局部变量存放在 JVM 栈的局部变量表中,基本数据类型的成员变量(未被 static 修饰)存放在 JVM 的堆中,因为包装类型属于对象类型,几乎都存放在堆中。
装箱和拆箱
自动拆箱和装箱从 Java1.5 开始引入,目的是为了让原始类型和对应的包装类对象之间可以自动的相互转换。
实现原理
- 装箱:调用了包装类的 valueOf 方法;
- 拆箱:调用了包装类的 xxxValue 方法(xxx 代表对应的基本数据类型);
编译器会自动调用两个方法实现原始数据类型和包装类对象之间的转换。
1 | // 装箱 |
触发时机
赋值
1 | /** |
方法调用
1 | /** |
调用show(3)
时,会将int
自动装箱为Integer
。使用show
的返回值时,会自动将Integer
拆箱为int
。
使用注意
循环中的自动装箱和拆箱
1 | /** |
上述的代码中,Integer
和int
数据相加时,会发生自动拆箱和装箱。首先要对sum
进行自动拆箱,数据相加结束后再进行自动装箱转换为Integer
。流程可以概括为:
1 | int result = sum.intValue() + i; |
在上面的循环中,会频繁创建很多无用的Integer
对象,提高垃圾回收的工作量和导致程序性能下降。所以在日常的使用中需要注意避免不必要的自动拆箱和装箱。
包装类对象和基本数据类型的比较
当包装类进行算术运算或者与基本数据类型进行比较时,会自动拆箱或装箱。
1 | /** |