hashCode和equals两个方法一起使用可以判断是否为同一个对象。
他们的运作原理就是,首先判断hashCode是否相同,如果不同,直接判定为两个不同的对象。如果hashCode相同,再去比较equals是否一样,如果一样,则为同一个对象。如果不一样,则是两个不同对象。
接下来,我们重写两种方法,验证一下。
建两个类
public class Student {
public String no;
public String name;
public String getNo() {
return no;
}
public void setNo(String no) {
this.no = no;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
Student(String no, String name){
this.no=no;
this.name=name;
}
}
public class HashSetDemo {
private static Object Iteratorit;
public static void main(String args[]){
Set<Student> studentSet = new HashSet<Student>();
studentSet.add(new Student("001","ALLEN"));
studentSet.add(new Student("002","Caroline"));
studentSet.add(new Student("001","ALLEN"));
Iterator<Student> it =studentSet.iterator();
while(it.hasNext()){
Student student = it.next();
System.out.println(student.getNo()+"\t"+student.getName()+"\n");
}
}
}
运行一下看结果
可以看到,001 ALLEN两个相同的元素都被加进了Set中,为了避免这种请看,我们先试着在Student类里重写equals方法
public boolean equals(Object object){
if(!(object instanceof Student)){
return false;
}
Student student = (Student)object;
System.out.println("重写了equals方法");
return this.no.equals(student.no)&&this.name.equals(student.name);
}
再运行结果
结果并没有变化,而且可以看到他并没有调用equals方法。
这是因为,再Demo类中new的三个对象都有着不同的hashCode,这样直接被判定为三个不同的对象,所以并没有再去调用equals方法。
接下来,我们就去Student类里重写hashCode方法
public int hashCode(){
System.out.println("重写了hashCode方法");
return Integer.valueOf(this.no);
}
再运行结果
这是我们发现,Set中只存在两个对象,001 ALLEN不再出现两次。
因为在重写后的hashCode方法中,二者的hashCode被我们设置成了一样的值。
程序接着又去比较equals方法,发现结果还是一样的。
所以两种方法综合来看Set遇到了两个一样的对象,所以只有其中一个被真正的加进Set中。