1. 程式人生 > >Java中那些不得不說的坑

Java中那些不得不說的坑

看看下面這段程式碼跟你想的結果一樣嗎?

        Integer a =127;
        Integer b = 127;
        System.out.println(a==b);//true

        Integer a1 = 128;
        Integer b1 = 128;
        System.out.println(a1==b1);//false

為什麼會是這樣的結果,我們反編譯.class檔案看看

    Integer a = Integer.valueOf(127);
    Integer b = Integer.valueOf(127
); System.out.println(a == b); Integer a1 = Integer.valueOf(128); Integer b1 = Integer.valueOf(128); System.out.println(a1 == b1);

其實是Integer作者在寫這個類時,為了避免重複建立物件,對一定範圍的Integer做了快取,如果該值沒有在該範圍內則new一個新物件返回,從原始碼中可以看到如下程式碼:

    public static Integer valueOf(int i) {
        if (i >= IntegerCache.low && i <= IntegerCache.high)
            return
IntegerCache.cache[i + (-IntegerCache.low)]; //i如果在該範圍內直接返回快取值 return new Integer(i); }

IntegerCache 是Integer 類的靜態內部類,再來看看IntegerCache的實現

 private static class IntegerCache {
        static final int low = -128;
        static final int high;
        static final Integer cache[];

        static
{//當類被載入到java虛擬機器是進行快取建立 // high value may be configured by property int h = 127; String integerCacheHighPropValue = sun.misc.VM.getSavedProperty("java.lang.Integer.IntegerCache.high"); if (integerCacheHighPropValue != null) { try { int i = parseInt(integerCacheHighPropValue); i = Math.max(i, 127); // Maximum array size is Integer.MAX_VALUE h = Math.min(i, Integer.MAX_VALUE - (-low) -1); } catch( NumberFormatException nfe) { // If the property cannot be parsed into an int, ignore it. } } high = h; cache = new Integer[(high - low) + 1]; int j = low; for(int k = 0; k < cache.length; k++) cache[k] = new Integer(j++); // range [-128, 127] must be interned (JLS7 5.1.7) assert IntegerCache.high >= 127; } private IntegerCache() {} }