Integer.valueOf(...)

Integer.valueOf(…)

valueOf(String s, int radix)

public static Integer valueOf(String s, int radix) throws NumberFormatException {
    // 以 radix 进制。
    return Integer.valueOf(parseInt(s,radix));
}

valueOf(String s)

public static Integer valueOf(String s) throws NumberFormatException {
    // 1. 调用静态方法 parseInt() 将 s 以十进制转为 int 类型。
    // 2. 调用 valueOf(int i) 将 1 的结果转为 Integer。
        return Integer.valueOf(parseInt(s, 10));
}

valueOf(int i) - 重点

public static Integer valueOf(int i) {
    // 判断所要转换的 i 是否在缓冲池当中。
    if (i >= IntegerCache.low && i <= IntegerCache.high)
        // 如果存在,则之间将缓冲池中的对象的引用返回。
        return IntegerCache.cache[i + (-IntegerCache.low)];
    // 如果不存在,则新建一个对象,返回新建对象的引用。
    return new Integer(i);
}

IntegerCache

private static class IntegerCache {
    static final int low = -128;
    static final int high;
    
    // 声明一个 final 的缓存区间。
    static final Integer cache[];

    static {
        // high value may be configured by property
        int h = 127;
        // sun.misc.VM.getSavedProperty() 获取 Integer 所设置的缓存池大小。
        String integerCacheHighPropValue =
            sun.misc.VM.getSavedProperty("java.lang.Integer.IntegerCache.high");
        if (integerCacheHighPropValue != null) {
            try {
                // 将 integerCacheHighPropValue 转为 int 类型。
                int i = parseInt(integerCacheHighPropValue);
                
                // 获取 i 和 127 之间的最大值。
                i = Math.max(i, 127);
                // Maximum array size is Integer.MAX_VALUE
                // public static final int   MAX_VALUE = 0x7fffffff = 2,147,483,647‬	int 类型的最大值。
                /*
                 * 为什么 MAX_VALUE 需要 -(-low) - 1 ?
                 * 1. 缓冲区的大小只能设置上限 high,不能设置下限 low。
                 * 2. i 为系统设置的缓冲区的上限,而不是缓冲区大小,默认为 127。
                 *	  1. 缓冲区大小为:high - low + 1。
                 * 3. MAX_VALUE 需要减去 low 和 1 之后才是缓冲区的上限,减去之前是缓冲区的最大容量。
                 * 4. 所以是将最大上限和系统设置的上限比较,取较小者。
                */
                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;	// 如果没有手动设置缓存区的大小,则 high = 127;
		
/********************************************************************************
         * 以下分析均假设为:没有手动设置缓存区的大小:
********************************************************************************/
        
        // 指定缓存数组 cache 的大小:127 - (-128) + 1 = 256
        cache = new Integer[(high - low) + 1];
        int j = low;
        
        // 初始化 cache 数组,将 -128 , 127 保存到 cache 数组中。
        // cache.length == 256
        for(int k = 0; k < cache.length; k++)
            cache[k] = new Integer(j++);
        // 索引:值  0:-128  1:-127  127:-1  128:0  129:1  255:127

        // range [-128, 127] must be interned (JLS7 5.1.7)
        // assert:断言,这个关键字可以判断布尔值的结果是否和预期的一样,
        // 如果一样就正常执行,否则会抛出 AssertionError。
        assert IntegerCache.high >= 127;
    }
	
    // 私有构造方法:证明 IntegerCache 此类不希望被其他类所使用。
    private IntegerCache() {}
}

总结

  1. IntegerCacheInteger 类中的 私有 静态 内部 类。

  2. IntegerCache 相当于一个缓存,内部定义了一个缓冲区 cache,存储 Integer 类型对象的引用,默认区间为 [-128, 127],可手动设置上限,但不可设置下线。

  3. valueOf(int i)

    1. 先判断参数 i 是否在缓冲区间内:
    2. 如果在,则从 IntegerCache 中直接返回缓冲区中对于对象的引用。
    3. 如果不在,则新建一个对象,并返回引用。

Integer 对象比较问题

public static void main(String args[]) {
    Integer a1 = 127;
    Integer a2 = 127;
    System.out.println(a1 == a2); // true

    Integer b1 = 128;
    Integer b2 = 128;
    System.out.println(b1 == b2); // false
}
  1. a1 a2[-128, 127] 范围内,所以指向缓冲区中同一个对象。
  2. b1 b2 不在 [-128, 127] 范围内,所以,分别指向不同的对象。

建议使用 equals 进行对象之间的比较。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值