Integer、Long等基本类型的包装类比较时的注意点

先来看一段代码:
Integer a = 1;
Integer b = 1;
System.out.println(a == b);     // true
 
Integer aa = 128;
Integer bb = 128;
System.out.println(aa == bb);   // false
 
为什么输出结果是这样?这就跟Integer创建对象的方式有关了。在使用 Integer 创建对象的过程中,首先会调用valueOf()方法,源码如下
public static Integer valueOf(int i) {
    if (i >= IntegerCache.low && i <= IntegerCache.high)
        return IntegerCache.cache[i + (-IntegerCache.low)];
    return new Integer(i);
}
Integer会对传入的参数进行了一个判断,在-128<i<127时直接从IntegerCache缓存中取,而当超出这个范围时,则在堆中新建了一个对象。
因此,上面代码中a 和 b 实际上都指向了IntegerCache中的同一个地址,而aa 和 bb 超过了-128~127这个范围,它们指向了堆中不同的对象。
 
Long.vlaueOf()源码
public static Long valueOf(long l) {
    final int offset = 128;
    if (l >= -128 && l <= 127) { // will cache
        return LongCache.cache[(int)l + offset];
    }
    return new Long(l);
}
可以看到,Long同样如此
 
所以,当我们在对这些包装类进行比较时,应该使用equals进行比较,这样就能避免这些意外情况发生。
Integer aa = 128;
Integer bb = 128;
System.out.println(aa.equals(bb));   // true
 
posted @ 2019-10-10 13:07  半城烟雨一城湖  阅读(960)  评论(0编辑  收藏  举报