理解“==”和“equals”、hashcode方法
1、“=="和equals方法
在object类中,equals方法其实就是==方法
但是,在大部分的类中,都重写了equals方法和hashcode方法(后面会说),所以equals方法才会比较值是否相等,但是自定义的类,例如你自己定义的person,student类,自然是没重写equals和hashcode的。
2、为什么重写了equals方法,就要重写hashcode方法
第一:因为hashcode的协定,hashcode有如下协定:
- 两个对象相等,hashcode一定相等
- 两个对象不等,hashcode不一定不等
- hashcode相等,两个对象不一定相等
- hashcode不等,两个对象一定不等
如果只重写了equals方法,那么可能导致两个相等的类,调用equals方法相等,但是hashcode不等,自然也就违背了这个协定
第二:为了hash类的集合,例如hashmap,hashset等,这一类在判定两个对象是否相同时,会先调用hashcode,hashcode相同后,才会调用equals方法,但是如果只重写了equals方法,可能这个equals是相等的,但是默认调用object生成的hashcode是不相等的,从而导致两个本来应该值相等的对象,都插入到了set集合中,这就违背了开发人员的初衷
3、hashcode的作用
通过哈希算法(散列算法),让每个不相等的对象,生成不同的int类型的值,先比较int类型的值,如果相同再通过equals方法进行比较,这样子能提高查找的效率,
4、举个例子
Student s1=new Student("小秋",21);
Student s2=new Student("小秋",21);
程序员想要的效果,肯定是s1要和s2相等,但是在程序看来,s1和s2是两个不同的对象,所以程序员为了让机器把s1和s2看成相同的对象,所以要重写equals方法
加入要把s1和s2存入到hashset中,那么重写equals方法还不够,因为hashset默认会先调用hashcode方法,判断是否相同,如果相同,才会再判断equals方法
但是object的hashcode方法,默认是用地址生成的值,s1和s2是分别new出来的,地址自然不相等,hashcode值也就不相等了
这样子就会导致,hashset里面会把s1和s2都存进去,但是实际上,我们只需要存入一个就够了。
如果有不对的地方,还望各位大佬批评指正! |