细节问题2:Integer什么时候会使用常量池里的值什么时候会new一个?

细节问题2:Integer什么时候会使用常量池里的值什么时候会new一个?

package classandobject;

public class Integer_Int {
    public static void main(String[]args){
        // 1)基本类型和包装类型
        int a = 100;//字面量
        Integer b = 100;//自动装箱,但是100在-128到127之间(一个字节大小的范围),使用常量池存放,new一个会作为共享,节省空间
        System.out.println(a == b);//b拆箱,这里就是比较值的大小了。true

        // 2)两个包装类型
        Integer c = 100;//自动装箱,但是100在-128到127之间,地址引用,直接拿b来用
        Integer d = 100;//自动装箱,但是100在-128到127之间,常量池已经有了,直接拿b的值来用
        System.out.println(c == d);//true,地址引用相同
        System.out.println(c==b);//true,地址引用相同
        System.out.println(c==a);//true 自动拆箱
        Integer c_new = new Integer(100);
        System.out.println(c_new==c);//false,因为地址引用不同
        // 3)常规量
        c = 200;//c = c.valueOf(200),200不在-128到127之间,所以会使用new创建对象
        d = 200;//也就是说这里c,d都使用了new,

        System.out.println(c == d);//使用new创建的对象地址引用不同,false
        System.out.println(c.equals(d));//比较的是值,true

    }
}

在这里插入图片描述

解析
之前我们已经知道了,自动装箱是通过 Integer.valueOf() 完成的,那我们就来看看这个方法的源码吧。

public static Integer valueOf(int i) {
    if (i >= IntegerCache.low && i <= IntegerCache.high)//low=-128,high = 127,一个字节的范围 
        return IntegerCache.cache[i + (-IntegerCache.low)];//使用常量池里边的数
    return new Integer(i);//否则重新new一个
}
//我们来看一下条件是什么:
private static class IntegerCache {
    static final int low = -128;
    static final int high;
    static final Integer cache[];

    static {
        // high value may be configured by property
        int h = 127;
        int i = parseInt(integerCacheHighPropValue);
        i = Math.max(i, 127);
        h = Math.min(i, Integer.MAX_VALUE - (-low) -1);
        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;
    }
}

valueOf() 方法的实现比较简单,就是先判断值是否在缓存池中,如果在的话就直接返回缓存池的内容。在 Java 8 中,Integer 缓存池的大小默认为 -128~127。编译器会在自动装箱过程调用 valueOf() 方法,因此

多个值相同且值在缓存池范围内(-128~127)的 Integer 实例使用自动装箱来创建,那么就会引用相同的对象。
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

雨夜※繁华

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值