JAVA 自动装拆箱与Integer判断相等中的坑

学习了java中的自动装拆箱后我们知道基本类型和其对应的包装类之间再某些时候可以相互转换,例如:Integerint的相互转换:

/* 不用自动装箱的标准写法 */
Integer a1 = Integer.valueOf(100);
/* 自动装箱后实际上只需要这样写 */
Integer a2 = 100;

/* 不用自动拆箱的标准写法 */
int a3 = a1.intValue();
/* 自动拆箱后实际上只需要这么写 */
int a4 = a1;

注意:jvm在实际执行的还是第2、7行的代码,编译过程中为我们进行了自动装拆箱的转换

 

但是需要注意的是:不是任何时候都会发生自动装拆箱的过程,如:两个Integer之间使用如下方式比较大小

Integer a = 1;
Integer b = 1;
System.out.println(a == b);

使用“==”时不会自动拆箱,不会自动拆箱,不会自动拆箱。,所以实际上是两个Integer的内存地址的比较,而不是比较值。

那既然不会发生自动拆箱,那么上述结果会输出什么呢?答案是true。那么问题来了,既让不会发生自动拆箱即是比较的两个对象的地址,为什么不是false呢?

原来在java中有Integer常量池这个东西,它的作用是:

当你创建一个Integer对象时不会立马放回一个新的对象给你,而是判断创建的对象的值是否在-128~127之间如果是,那么将会从常量池中直接返回一个已存在的对象给你(如果常量池中没有则会先创建)。

注意:当使用 new 创建对象时,会在堆中创建对象并指向它,而不是指向常量池中的地址。

 

所以上面代码中a、b实际上都指向了常量池中的同一个地址,所以最终比较结果为true;当值在-128~127之外时结果为false。

Integer a = 128;
Integer b = 128;
Integer c = 127;
Integer d = 127;
/* 输出 a == b: false */
System.out.println("a == b: " + (a == b));
/* 输出 c == d: true */
System.out.println("c == d: " + (c == d));
/* 输出 a.equals(b): true */
System.out.println("a.equals(b): " + (a.equals(b)));
/* 输出 c.equals(d): true */
System.out.println("c.equals(d): " + (c.equals(d)));

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值