深入剖析Java中的裝箱和拆箱
阿新 • • 發佈:2020-08-10
請尊重作者勞動成果,轉載請標明原文連結:
什麼是裝箱?什麼是拆箱?
裝箱就是自動將基本型別轉換為包裝器型別;拆箱就是自動將包裝型別裝換位基本型別。
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)在執行效率和資源佔用上的區別。第二種方式的執行效率和資源佔用在一般性情況下要優於第一種情況(注意這並不是絕對的)。