黑马程序员技术交流社区

标题: 关于equals和==以及hashcode的一点总结 [打印本页]

作者: 李厚斌    时间: 2014-4-6 23:51
标题: 关于equals和==以及hashcode的一点总结
本帖最后由 李厚斌 于 2014-4-6 23:55 编辑

先看题。。。再出总结。这样容易记得。。如果你都正确那就不用看解释了。完全over了
  1. public class Tset

  2. {

  3.     public static void main(String[] args) {
  4.             String s1="abc";
  5.             String s2="abc";
  6.             System.out.println(s1==s2);
  7.             System.out.println(s1.equals(s2));
  8.             String s3=s2+"abc";
  9.             System.out.println(s3==s2+"abc");
  10.             System.out.println(s3.equals(s2+"abc"));
  11.             
  12.             String s4=s1+s2;
  13.             System.out.println(s4==s1+s2);
  14.             System.out.println(s4=="abcabc");
  15.             String s5=new String("abcabc");
  16.             System.out.println(s5==s4);
  17.             System.out.println(s5=="abcabc");
  18.             String s6="abcabc";
  19.             System.out.println(s6=="abc"+"abc");
  20.             System.out.println(s6==s1+s2);
  21.             Integer i1=5;
  22.             Integer i2=new Integer(5);
  23.             Integer i3=5;
  24.             System.out.println(i1==i2);
  25.             System.out.println(i1.equals(i2));
  26.             System.out.println(i1==i3);
  27.             Integer i4=1228;
  28.             Integer i5=1228;
  29.             System.out.println(i4==i5);
  30.             System.out.println(i4.equals(i5));
  31.     }

  32. }
复制代码
运行结果:true
true
false
true
false
false
false
false
true
false
false
true
true
false
true


1:==可用于基本类型和引用类型:当用于基本类型时候,是比较值是否相同;当用于引用类型的时候,是比较对象是否相同。
2:对于String a = “a”; Integer b = 1;(只针对-128---127.超过这个范围的不行。在这个范围内和String类似有专门开辟的内存空间)这种类型的特有对象创建方式,==的时候值是相同的。
3:.基本类型没有equals方法,equals只比较值(对象中的内容)是否相同(相同返回true)。
4:.一个类如果没有定义equals方法,它将默认继承Object中的equals方法,返回值与==方法相同。
详述:
String str1 = "abc";
String str2 = "abc";
String str3 = str1+str2;   //这种创建方式是不放入字符串池的.这种情况表示str1+str2每次相加都会产生一个新对象储存在栈内存中。
下面的str4和str5一样的。也是每次相加都会产生一个新对象储存在栈内存中。所以每次相加的引用地址都是变换的也就是不相等的。
String str4 = str1+"cd";   //这种创建方式是不放入字符串池的.
String str5 = "ab"+str2;   //这种创建方式是不放入字符串池的.
String str6 = "ab"+"cd"; //这种创建方式是放入字符串池的.这种情况实际上是创建了1个对象,abcd"1个对象。
这样就对上面的题有个认识了吧。

String s2="abc";
String s3=s2+"abc";
        System.out.println(s3==s2+"abc");所以这个是false

String s4=s1+s2;
            System.out.println(s4==s1+s2); false str1+str2每次相加都会产生一个新对象储存在栈内存中。。前后的引用地址是不一样的
            System.out.println(s4=="abcabc"); false s4指向的是栈内存的引用地址。“abcabc”指向的常量池。

String s6="abcabc";
            System.out.println(s6=="abc"+"abc");这个是ture 。
            System.out.println(s6==s1+s2); false

Integer i4=1228;
Integer i5=1228;
            System.out.println(i4==i5);false 超出了限制范围(-128---127)
            System.out.println(i4.equals(i5));复写了equals方法。之比较内容是否相等。所以是ture


”==“其实总结一句话:看对象的引用地址指向的是哪里。。如果指向常量池。。内容相等那肯定相等。
如果一个指向常量池一个指向栈内存。。不相等。两个都指向栈内存。。如果新创建对象则不相等。引用地址变化了不管内容变化不变化。


看了好几篇博客都这么写的。。其实是不正确的。。因为equals()和hashCode()是两个可以随便复写的方法。怎么能这么说呢。
结论:对于equals()相等的两个对象,其hashCode()返回的值一定相等
  1. class Person{
  2.         private String name;
  3.         @Override
  4.         public String toString() {
  5.                 return "Person [name=" + name + ", age=" + age + "]";
  6.         }
  7.         private int age;
  8.         Person(String name,int age){
  9.                 this.name=name;
  10.                 this.age=age;
  11.         }
  12.         @Override
  13.         public int hashCode(){
  14.                 return new Random().nextInt(10)*age;
  15.         }
  16.         @Override
  17.         public boolean equals(Object obj){
  18.                 Person p=(Person)obj;
  19.                 return name.equals(p.name)&&age==p.age;
  20.         }
复制代码
  1. HashSet hs=new HashSet();
  2.             hs.add(new Person("lisi",45));
  3.             hs.add(new Person("lisi",45));
  4.             hs.add(new Person("lisi",45));
  5.             System.out.println(hs.size());
复制代码
size打印结果是3
表示三个都加进去了。。hashset集合是根据hashcode排列。。如果hashcode相等然后判断equals方法。。如果equals方法表示两个对象true才、、、才判断是重复元素。上面例子。add添加的对象equals全部都是相等。。但是hashcode不相等。所以能添加进去。反驳了“对于equals()相等的两个对象,其hashCode()返回的值一定相等”这句话





作者: 2528870651    时间: 2014-4-7 22:09
顶一个!!!
作者: 冷月    时间: 2014-4-9 09:11
赞一个!!!!!!!
作者: 种一棵树    时间: 2014-4-9 09:29
赞一个,谢谢分享
作者: dunami    时间: 2014-4-9 22:49
感谢分享 学到了




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2