先看代码
- public static void main(String[] args) {
- Integer one = 127;
- Integer two = 127;
- System.out.println(one == two);
-
- Integer one_1 = 128;
- Integer two_1 = 128;
- System.out.println(one_1 == two_1);
-
- }
打印结果如下
哎~,这就奇怪了,都是数字,同样符号来判断,竟然会有不同的结果;
当我看源码之后才知道,当我写下这段代码
Integer one = 127;
但其实,在底层的代码其实是这样的
Integer one = Integer.valueOf(127);
这时候我们进去 valueOf() 这个方法看看
一切都恍然大悟了,原来啊,jdk 将 -128 ~ 127 这个范围的数字都缓存起来了;IntegerCache 是 Integer 里的一个内部静态类,存储了 -128 ~ 127 这个范围的数字,所以当我们使用这个范围内的数字的时候,其实是直接将缓存里面的值拿出来直接用了,这个范围内的数字都是用同一个内存地址的,所以用它们来作为==判断的话,肯定为true了,但128这个数字显然不在缓存里面,所以就需要new一个新的对象出来,因为我使用了2个128的对象,这2个对象就会new 两次,每次都用了不同的内存地址;用来判断肯定就是false了
接下来我们用其他的数据类型看看,发现都是一样的,
Short
- public static void main(String[] args) {
- Short one = 127;
- Short two = 127;
- System.out.println(one == two); // 打印 true
-
- Short one_1 = 128;
- Short two_1 = 128;
- System.out.println(one_1 == two_1); // 打印 false
- }
看看Short类的 valueOf() 方法,也缓存了 -128 ~ 127 这个范围的数字
Long
- public static void main(String[] args) {
- Long one = 127l;
- Long two = 127l;
- System.out.println(one == two); // 打印 true
-
- Long one_1 = 128l;
- Long two_1 = 128l;
- System.out.println(one_1 == two_1); // 打印 false
- }
看看Long 类的 valueOf() 方法,发现也缓存了 -128 ~ 127 这个范围的数字
问题
那么问题来了,jdk为什么要把-128 ~ 127 这个范围的数字给缓存起来呢? 难道是吃饱了撑的?
- 因为我们这些数字是我们用的比较高频的数字,jdk这么做也是为了节省资源,如果每个数字都初始化一遍,那么在内存空间里面不就需要占用大量的资源了嘛
- 而且也是为了方便垃圾回收机制,毕竟gc回收也是需要时间的,jdk优化的首要条件就是尽可能的减少垃圾回收的次数,如果我们不用这些缓存,那么无疑会在内存里面产生大量的垃圾等着gc去回收,既然开发jdk的人已经想到了这种优化方式,也是一种很好得节省内存空间得方法!