深入剖析Java中的装箱和拆箱
请尊重作者劳动成果,转载请标明原文链接:
什么是装箱?什么是拆箱?
装箱就是自动将基本类型转换为包装器类型;拆箱就是自动将包装类型装换位基本类型。
int(4字节) | Integer |
byte(1字节) | Byte |
short(2字节) | Short |
long(8字节) | Long |
float(4字节) | Float |
double(8字节) | Double |
char(2字节) | Character |
boolean | Boolean |
装箱和拆箱是如何实现的
1 public class Main { 2 public static void main(String[] args) { 3 4 Integer i = 10; 5 int n = i; 6 } 7 }
在装箱的时候调用的是Integer的ValueOf(int)方法。而拆箱的时候自动调用的是Integer的initValue()方法。
因此可以总结为:
装箱过程调用包装饰器的ValueOf方法实现的,而拆箱过程是调用xxxValue()实现的。
面试中的相关问题
1 public class Main { 2 public static void main(String[] args) { 3 4 Integer i1 = 100; 5 Integer i2 = 100; 6 Integer i3 = 200; 7 Integer i4 = 200; 8 9 System.out.println(i1==i2); 10 System.out.println(i3==i4); 11 } 12 }
答案为 true 、false
分析如下:这个时候得分析Integer.ValueOf的具体实现:
public static Integer valueOf(int i) { if(i >= -128 && i <= IntegerCache.high) return IntegerCache.cache[i + 128]; else return new Integer(i); }
而其中IntegerCache类的实现为:
1 private static class IntegerCache { 2 static final int high; 3 static final Integer cache[]; 4 5 static { 6 final int low = -128; 7 8 // high value may be configured by property 9 int h = 127; 10 if (integerCacheHighPropValue != null) { 11 // Use Long.decode here to avoid invoking methods that 12 // require Integer's autoboxing cache to be initialized 13 int i = Long.decode(integerCacheHighPropValue).intValue(); 14 i = Math.max(i, 127); 15 // Maximum array size is Integer.MAX_VALUE 16 h = Math.min(i, Integer.MAX_VALUE - -low); 17 } 18 high = h; 19 20 cache = new Integer[(high - low) + 1]; 21 int j = low; 22 for(int k = 0; k < cache.length; k++) 23 cache[k] = new Integer(j++); 24 } 25 26 private IntegerCache() {} 27 }
从这2段代码可以看出,在通过valueOf方法创建Integer对象的时候,如果数值在[-128,127]之间,便返回指向IntegerCache.cache中已经存在的对象的引用;否则创建一个新的Integer对象。
上面的代码中i1和i2的数值为100,因此会直接从cache中取已经存在的对象,所以i1和i2指向的是同一个对象,而i3和i4则是分别指向不同的对象。
-
谈谈Integer i = new Integer(xxx)和Integer i =xxx;这两种方式的区别。
1)第一种方式不会触发自动装箱的过程;而第二种方式会触发;
2)在执行效率和资源占用上的区别。第二种方式的执行效率和资源占用在一般性情况下要优于第一种情况(注意这并不是绝对的)。
Stay foolish!Stay hungry!