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

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 胡奎 中级黑马   /  2012-5-6 14:45  /  3023 人查看  /  6 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

[code]public static void main(String[] args) {
                // TODO Auto-generated method stub
                Integer i = 3;
                Integer j = 3;
               
                System.out.println(i == j);
                System.out.println(i.equals(j));
               
                Double b1 = 3.0;
                Double b2 = 3.0;
               
                System.out.println(b1 == b2);
                System.out.println(b1.equals(b2));
        }

打印结果 true true false true

既然Integer中比较都相等,Double的为啥不相等呢?

6 个回复

正序浏览
float 和double没有享元模式,而其他的都有享元模式
例如:
integer类型Byte类型Short类型Long类型,都支持享元模式
当数值-128~127时就是相同的对象,在这个范围之外就是不同对象,所以就出现上述问题。
而Byte类型时,如果大于这个范围,就会报不兼容的类型需要int(。。)
回复 使用道具 举报
楼主,我把八种基本数据类型所对应的类 全试了一遍,代码很简单了,如下:
public class Test {
        public static void main(String[] args){

    Integer i = 3;
    Integer j = 3;
    System.out.println(i == j);

    Long l1 = 2l;
    Long l2 = 2l;
    System.out.println(l1 == l2);
   
   
    Short s1 = 3;
    Short s2 = 3;
    System.out.println(s1 == s2);
   
    Boolean bl1 = true;
    Boolean bl2 = true;
    System.out.println(bl1 == bl2);
   
    Byte be1 = 23;
    Byte be2 = 23;
    System.out.println(be1 == be2);
   
    Character c1 = 's';
    Character c2 = 's';
    System.out.println(c1 == c2);
   
    //从这里开始为false
    Float f1 = 3f;
    Float f2 = 3f;
    System.out.println(f1 == f2);
   
    Double b1 = 3d;
    Double b2 = 3d;
   
    System.out.println(b1 == b2);
        }

}


运行结果呢:  true  true  true  true true  true  false false

发现只有Float 和Double 不同,百度了一下,找不到,也希望哪位大神能来解释解释下:::

回复 使用道具 举报
你这个问题真是前无古人!
我debug了一下,发现了问题!(如图)
在语句:Integer i = 3;处设置断点,发现执行完语句Double b2 = 3.0;后
b1与b2的id不相等(不是同一个对象——false),而i与j的id相等(是同一个对象——true
感觉非常奇怪!

2012-05-06_153904.png (34.73 KB, 下载次数: 26)

2012-05-06_153904.png
回复 使用道具 举报
因为Double不知基本数据类型,而==的作用原理
==:对于基本数据类型,盘对值是否相等。  对于非基本数据类型,判断地址是否相当
注意,double是基本数据类型,但是Double就不是了
  就像int与Integer一样。
而关于 eqluas
equals()方法,该方法定义在Object 类当中,因此Java 中的每个类都具有该方法,对于Object 类的equals()方法来说,它是判断调用equals()方法的引用与传进来的引用是否一致,即这两个引用是否指向的是同一个对象。对于 Object 类的equals()方法来说,它等价于==。
对于 String 类的 equals()方法来说,它是判断当前字符串与传进来的字符串的内容是否一致。 对于String 对象的相等性判断来说,请使用equals()方法,而不要使用== 。
回复 使用道具 举报
对于基本数据类型的整数,要装箱成Integer对象的时候,如果这个数字在一个字节之内,也就是-128到127之间的数字,一旦被包装成Integer对象之后,就会把它缓存起来,在一个池里面。当下次又要把一个整数包装成Integer对象的时候,就会先要到缓存池里面看有没有这个数,如果有就从缓存池里面取,这样就节省了内存空间。所以指向的是同一个对象
其实这是一种设计模式,叫享元模式。
回复 使用道具 举报
==比较的是地址值,包装类的equals是比较数值
由于Float和Double的结构特殊,所以他们不在常量池中,其它的包装类对象直接装箱的话数值都在常量池中
不知道LZ对常量池知道不,前面的Integer将数值3装箱到了对象i,j中,3在常量池中,所以i,j指向了相同对象,地址值和数值都相等
如果Integer i = new Integer(3);
Integer j = new Integer(3);
那么 i == j 就是false
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马