Java装箱、拆箱

时间: 作者:走吧走吧

概念

  • 装箱和拆箱

    装箱:把基本类型用它们相应的引用类型包装起来,使其具有对象的性质。int包装成Integer、float包装成Float
    拆箱:和装箱相反,将引用类型的对象简化成值类型的数据

  • 基本数据类型与对象的差别

    基本数据类型不是对象,也就是使用int、double、boolean等定义的变量、常量。
    基本数据类型没有可调用的方法。
    eg: int t = 1; t. 后面是没有方法滴。
    Integer t =1; t. 后面就有很多方法可让你调用了。

八种基本类型

Integer的自动装箱/拆箱

1
2
3
4
5
6
Integer i1 = 200;
Integer i2 = 200;
System.out.println("i1==i2: " + (i1 == i2));
Integer i3 = 100;
Integer i4 = 100;
System.out.println("i3==i4: " + (i3 == i4));

输的结果是:
i1==i2: false
i3==i4: true

  • equals() 比较的是两个对象的值(内容)是否相同。
    “==” 比较的是两个对象的引用(内存地址)是否相同,也用来比较两个基本数据类型的变量值是否相等。

int 的自动装箱,是系统执行了 Integer.valueOf(int i),先看看Integer.java的源码:

1
2
3
4
5
6
public static Integer valueOf(int i) {
    if(i >= -128 && i <= IntegerCache.high)  // 没有设置的话,IngegerCache.high 默认是127
        return IntegerCache.cache[i + 128];
    else
        return new Integer(i);
}

对于–128到127(默认是127)之间的值,Integer.valueOf(int i) 返回的是缓存的Integer对象(并不是新建对象)
所以范例中,i3 与 i4实际上是指向同一个对象。
而其他值,执行Integer.valueOf(int i) 返回的是一个新建的 Integer对象,所以范例中,i1与i2 指向的是不同的对象。

Integer、Short、Byte、Character、Long这几个包装类的valueOf方法的实现是类似的。
Double、Float的valueOf方法的实现是类似的。
Boolean的valueOf方法的实现是个三目运算,形如return (b ? TRUE : FALSE);

1
2
3
4
5
6
7
8
9
10
11
Integer i1 = 17;
int i2 = 17;

int i3 = 137;
Integer i4 = 137;

System.out.println(i1 == i2); //true
System.out.println(i3 == i4); //true

System.out.println(i1.equals(i2)); //true
System.out.println(i3.equals(i4)); //true

当包装器类型和基本数据类型进行“==”比较时,包装器类型会自动拆箱为基本数据类型。

1
2
3
4
5
6
7
//Integer类的equals方法
public boolean equals(Object obj) {
if (obj instanceof Integer) {
return value == ((Integer)obj).intValue();
}
return false;
}

Integer、Short、Byte、Character、Long这几个包装类的intValue方法的实现是类似的。
Double、Float的intValue方法的实现是类似的。
Boolean的booleanValue方法的实现和intValue方法的实现也是类似的。

参考文章

java 自动装箱与拆箱
java 拆箱与陷阱
快看吧