A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

我们知道对于小于127的整数,jvm会对他进行自动装箱和拆箱。
Integer i=5; Integer j=5;
boolean b=i==j;//此时为true,Integer类型的i,j被自动拆箱成int型,若此时不拆箱将会是两对象相比,结果会是false,想问这里是不是一定要拆箱来比较?但等号两边可以是引用类型比较啊。

boolean bb=i.equals(j);//true

又如:


int i=5;
int j=5;
boolean b=i==j;//true,为啥这里i,j不会被自动装箱成Integer类型来比较?若是那结果将会是false
boolean bb=i.equals(j);//编译时这里提示i,j为基本类型的错误,我想问为什么此时jvm不把i,j自动装箱成Integer类型了??

评分

参与人数 1技术分 +1 收起 理由
职业规划-刘倩老师 + 1 赞一个!

查看全部评分

1 个回复

倒序浏览
本帖最后由 田啸 于 2012-3-3 00:18 编辑

感觉首先你对==  和equals 不是很清楚,先看看  ==  和equals 的区别:

==  在操作数是基本数据类型时,是比较值是否相等,在操作数是引用类型时,比较的是是否指向堆中同一个对象。

equals是object的普通方法,object是所有类的基类,不同的类,重写equals的方法不同,基本数据类型当然没这个方法,所以会提示你i,j为基本类型的错误

然后看下Integer的equals:

01.public boolean equals(Object obj) {  
02.    if (obj instanceof Integer) {  
03.        return value == ((Integer)obj).intValue();  
04.    }  
05.    return false;  
06.    }  

自动装箱其实就是编译器编译的时候,自动帮你把int变成Integer对象,调用的是Integer的静态方法valueOf(),看反编译过来的代码就可以看出:
01.public static Integer valueOf(int i) {  
02.        if(i >= -128 && i <= IntegerCache.high)  
03.            return IntegerCache.cache[i + 128];  
04.        else  
05.            return new Integer(i);  
06.    }  

当你调用这个方法,把int变成Integer的时候,是有规则的,当你的int的值在-128-IntegerCache.high(127) 时,返回的不是一个新new出来的Integer对象,而是一个已经缓存在堆中的Integer对象,(我们可以这样理解,系统已经把-128到127之间的Integer缓存到一个Integer数组中去了,如果你要把一个int变成一个Integer对象,首先去缓存中找,找到的话直接返回引用给你就行了,不必再新new一个)。

包装类的==操作在没有遇到算术运算的情况下,不会自动拆箱:
当==2边是包装类的时候,其实包装类就是对象,比较的是2个对象引用是否指向同一个对象,如果2边有一个是基本数据类型的话,那么就是比较值大小,这个优先级更高,既然是比较值大小,那么自然另一边的包装类就要拆箱成基本类型进行比较值大小了)
当==2边是基本数据类型,那就会直接比较大小,因此就不会自动装箱

回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马