hashCode与equals的区别与联系(经典)

合集下载

Java对象的equals()和hashCode()的使用

Java对象的equals()和hashCode()的使用

前言在Java语言中,equals()和hashCode()两个函数的使用是紧密配合的,你要是自己设计其中一个,就要设计另外一个。

在多数情况下,这两个函数是不用考虑的,直接使用它们的默认设计就可以了。

但是在一些情况下,这两个函数最好是自己设计,才能确保整个程序的正常运行。

最常见的是当一个对象被加入收集对象(collection object)时,这两个函数必须自己设计。

更细化的定义是:如果你想将一个对象A放入另一个收集对象B里,或者使用这个对象A为查找一个元对象在收集对象B里位置的钥匙,并支持是否容纳,删除收集对象B里的元对象这样的操作,那么,equals()和hashCode()函数必须开发者自己定义。

其他情况下,这两个函数是不需要定义的。

equals():它是用于进行两个对象的比较的,是对象内容的比较,当然也能用于进行对象参阅值的比较。

什么是对象参阅值的比较?就是两个参阅变量的值得比较,我们都知道参阅变量的值其实就是一个数字,这个数字可以看成是鉴别不同对象的代号。

两个对象参阅值的比较,就是两个数字的比较,两个代号的比较。

这种比较是默认的对象比较方式,在Object这个对象中,这种方式就已经设计好了。

所以你也不用自己来重写,浪费不必要的时间。

对象内容的比较才是设计equals()的真正目的,Java语言对equals()的要求如下,这些要求是必须遵循的。

否则,你就不该浪费时间:对称性:如果x.equals(y)返回是“true”,那么y.equals(x)也应该返回是“true”。

反射性:x.equals(x)必须返回是“true”。

类推性:如果x.equals(y)返回是“true”,而且y.equals(z)返回是“true”,那么z.equals(x)也应该返回是“true”。

还有一致性:如果x.equals(y)返回是“true”,只要x和y内容一直不变,不管你重复x.equals(y)多少次,返回都是“true”。

hashcode()和equals()方法详解,避免重复

hashcode()和equals()方法详解,避免重复

今天下午研究了半天hashcode()和equals()方法,终于有了一点点的明白,写下来与大家分享1. 首先equals()和hashcode()这两个方法都是从object类中继承过来的。

equals()方法在object类中定义如下:public boolean equals(Object obj) {return (this == obj);}很明显是对两个对象的地址值进行的比较(即比较引用是否相同)。

但是我们必需清楚,当String 、Math、还有Integer、Double。

等这些封装类在使用equals()方法时,已经覆盖了object类的equals()方法。

比如在String类中如下:public boolean equals(Object anObject) {if (this == anObject) {return true;}if (anObject instanceof String) {String anotherString = (String)anObject;int n = count;if (n == anotherString.count) {char v1[] = value;char v2[] = anotherString.value;int i = offset;int j = anotherString.offset;while (n-- != 0) {if (v1[i++] != v2[j++])return false;}return true;}}return false;}很明显,这是进行的内容比较,而已经不再是地址的比较。

依次类推Double、Integer、Math。

等等这些类都是重写了equals()方法的,从而进行的是内容的比较。

当然了基本类型是进行值的比较,这个没有什么好说的。

我们还应该注意,Java语言对equals()的要求如下,这些要求是必须遵循的:• 对称性:如果x.equals(y)返回是“true”,那么y.equals(x)也应该返回是“true”。

Java 中的 ==, equals 与 hashCode 的区别与联系

Java 中的 ==, equals 与 hashCode 的区别与联系

Java中的==,equals与hashCode的区别与联系(文章来源:北大青鸟成都锦江)一、概述1、概念∙== :该操作符生成的是一个boolean结果,它计算的是操作数的值之间的关系∙equals : Object 的实例方法,比较两个对象的content是否相同∙hashCode : Object 的native方法 , 获取对象的哈希值,用于确定该对象在哈希表中的索引位置,它实际上是一个int型整数二、关系操作符==1、操作数的值∙基本数据类型变量在Java中有八种基本数据类型:浮点型:float(4 byte), double(8 byte)整型:byte(1 byte), short(2 byte), int(4 byte) , long(8 byte)字符型: char(2 byte)布尔型: boolean(JVM规范没有明确规定其所占的空间大小,仅规定其只能够取字面值”true”和”false”)对于这八种基本数据类型的变量,变量直接存储的是“值”。

因此,在使用关系操作符== 来进行比较时,比较的就是“值”本身。

要注意的是,浮点型和整型都是有符号类型的(最高位仅用于表示正负,不参与计算【以byte 为例,其范围为-2^7 ~ 2^7 - 1,-0即-128】),而char是无符号类型的(所有位均参与计算,所以char类型取值范围为0~2^16-1)。

∙引用类型变量在Java中,引用类型的变量存储的并不是“值”本身,而是与其关联的对象在内存中的地址。

比如下面这行代码,String str1;这句话声明了一个引用类型的变量,此时它并没有和任何对象关联。

而通过new 来产生一个对象,并将这个对象和str1进行绑定:str1= new String("hello");那么str1 就指向了这个对象,此时引用变量str1中存储的是它指向的对象在内存中的存储地址,并不是“值”本身,也就是说并不是直接存储的字符串”hello”。

hashCode() 和equals() 区别和作用

hashCode() 和equals() 区别和作用

HashSet和HashMap一直都是JDK中最常用的两个类,HashSet要求不能存储相同的对象,HashMap要求不能存储相同的键。

那么Java运行时环境是如何判断HashSet中相同对象、HashMap中相同键的呢?当存储了“相同的东西”之后Java运行时环境又将如何来维护呢?在研究这个问题之前,首先说明一下JDK对equals(Object obj)和hashcode()这两个方法的定义和规范:在Java中任何一个对象都具备equals(Object obj)和hashcode()这两个方法,因为他们是在Object类中定义的。

equals(Object obj)方法用来判断两个对象是否“相同”,如果“相同”则返回true,否则返回false。

hashcode()方法返回一个int数,在Object类中的默认实现是“将该对象的内部地址转换成一个整数返回”。

接下来有两个个关于这两个方法的重要规范(我只是抽取了最重要的两个,其实不止两个):规范1:若重写equals(Object obj)方法,有必要重写hashcode()方法,确保通过equals(Object obj)方法判断结果为true的两个对象具备相等的hashcode()返回值。

说得简单点就是:“如果两个对象相同,那么他们的hashcode应该相等”。

不过请注意:这个只是规范,如果你非要写一个类让equals(Object obj)返回true而hashcode()返回两个不相等的值,编译和运行都是不会报错的。

不过这样违反了Java规范,程序也就埋下了BUG。

规范2:如果equals(Object obj)返回false,即两个对象“不相同”,并不要求对这两个对象调用hashcode()方法得到两个不相同的数。

说的简单点就是:“如果两个对象不相同,他们的hashcode可能相同”。

根据这两个规范,可以得到如下推论:1、如果两个对象equals,Java运行时环境会认为他们的hashcode一定相等。

java中equals和hashcode的区别【Java面试】

java中equals和hashcode的区别【Java面试】

(1)问题分析:考官主要想对hashCode()方法和equal()方法作用和效率上进行比较。

(2)核心答案讲解:equal()相等的两个对象他们的hashCode()肯定相等,也就用equal()对比可靠的。

hashCode()相等的两个对象他们的equal()不一定相等,也就hashCode()不可靠的。

对于需要量并且快速的对比的话如果都用equal()去显然效率太低,所以解决,每当需要对比的时候,首先用hashCode()去对比,如果hashCode()不一样,则表示这两个对象肯定不相等(也就不必再用equal()去再对比了),如果hashCode()相同,此时再对比他们的equal(),如果equal()也相同,则表示这两个对象真的相同了,这样既能提高了效率也保证了对比的正确性!(3)问题扩展:hashCode的重写:hashCode()和equal()一样都基本类Object里的方法,而和equal()一样,Object里hashCode()里面只返回当前对象的,如果这样的话,那么们相同的一个类,new两个对象,由于他们在内存里的不同,则他们的hashCode()不同,所以这显然不们想要的,所以们必须重写们类的hashCode()方法,即一个类,在hashCode()里面返回的一个hash值。

equals方法的作用:默认情况(没有覆盖equals方法)下equals方法都调用Object类的equals方法,而Object的equals方法主要用于判断对象的内存引用不同一个(不同一个对象);要类中覆盖了equals方法,那么就要根据具体的代码来确定equals方法的作用了,覆盖后一般都通过对象的内容否相等来判断对象否相等。

(4)结合中使用:equals方法默认的判断2个对象否相等的方法,在Object类里有实现,判断的2个对象的内存。

在hibernate中,不允许存在同类对象中有2个一样的实例。

equals方法和hashcode方法

equals方法和hashcode方法

equals方法和hashcode方法equals方法和hashcode方法是Java中两个重要的方法,它们在Java中的使用非常广泛,尤其是在集合框架中。

本文将从定义、作用、实现方式等方面详细介绍equals方法和hashcode方法。

一、equals方法1.定义equals方法是Object类中的一个方法,用于判断两个对象是否相等。

在Java中,所有的类都继承自Object类,因此所有的类都可以使用equals方法。

2.作用equals方法的作用是判断两个对象是否相等。

在Java中,相等的定义有两种:一种是引用相等,即两个对象的引用指向同一个内存地址;另一种是值相等,即两个对象的属性值相等。

equals方法默认使用引用相等进行比较,如果需要使用值相等进行比较,则需要在类中重写equals方法。

3.实现方式在Java中,重写equals方法需要满足以下条件:(1)自反性:对于任意的x,x.equals(x)应该返回true。

(2)对称性:对于任意的x和y,如果x.equals(y)返回true,则y.equals(x)也应该返回true。

(3)传递性:对于任意的x、y和z,如果x.equals(y)返回true,并且y.equals(z)也返回true,则x.equals(z)也应该返回true。

(4)一致性:对于任意的x和y,如果x.equals(y)返回true或false,则多次调用x.equals(y)应该返回相同的结果。

(5)非空性:对于任意的x,x.equals(null)应该返回false。

二、hashcode方法1.定义hashcode方法是Object类中的一个方法,用于返回对象的哈希码。

哈希码是一个整数,用于快速比较两个对象是否相等。

在Java中,哈希码通常用于集合框架中的散列表(HashMap、HashSet等)。

2.作用hashcode方法的作用是返回对象的哈希码。

哈希码可以用于快速比较两个对象是否相等,因为如果两个对象的哈希码不相等,则它们一定不相等。

ctf题解 equals和hashcode

ctf题解 equals和hashcode

ctf题解:equals和hashcode1. 背景介绍在进行ctf竞赛时,equals和hashcode是经常出现的一种题型,通常需要根据给出的代码和相关信息,来解答问题或解密密码。

equals 和hashcode是Java中用于比较对象和生成哈希码的两个方法,正确理解并使用它们对于解决ctf题目至关重要。

2. equals方法equals方法是用于比较两个对象的内容是否相同的方法,它的原型是```javapublic boolean equals(Object obj)```在重写equals方法时,需要注意以下几点:- 对象的比较顺序- 判空处理- 类型判断一个常见的equals方法的重写示例如下:```javaOverridepublic boolean equals(Object obj) {if (this == obj) {return true;}if (obj == null || getClass() != obj.getClass()) {return false;}// 比较对象的内容}```3. hashcode方法hashcode方法是用于生成对象的哈希码的方法,它的原型是```javapublic int hashCode()```在重写hashcode方法时,需要注意以下几点:- 哈希码相等对象不一定相等- 相等对象的哈希码一定相等- 哈希码尽可能分散一个常见的hashcode方法的重写示例如下:```javaOverridepublic int hashCode() {int result = // 根据对象的属性计算哈希码return result;}```4. ctf题目解析在ctf竞赛中,equals和hashcode题目常常涉及到对给定对象的equals和hashcode方法进行分析和求解。

参赛者需要根据给出的代码和相关信息,来判断两个对象是否相等或计算出其哈希码。

java 重写equals和hashcode方法

java 重写equals和hashcode方法

Java中的equals()和hashCode()方法是非常重要的方法,它们对于对象的比较和哈希值的计算起着至关重要的作用。

在使用Java开发中,我们经常需要重写这两个方法来确保对象的正确比较和哈希值的正确计算。

本文将介绍为什么需要重写equals()和hashCode()方法,以及如何正确地实现这两个方法。

1. 为什么需要重写equals()和hashCode()方法在Java中,所有的类都继承自Object类,而Object类中的equals()方法是用来比较对象的引用是否相等的,而hashCode()方法是用来返回对象的哈希值的。

在实际开发中,我们通常需要比较对象的内容是否相等而不是引用是否相等,同时也需要正确地计算哈希值以便于在集合中高效地查找对象。

2. equals()方法的重写实现equals()方法的重写时,通常需要遵循以下几个原则:2.1 使用instanceof关键字来判断是否为同一类型的对象。

2.2 对传入的参数进行null判断,并且判断是否为同一对象。

2.3 使用强制类型转换将Object类型转换为对应的类型,然后比较对象的内容是否相等。

我们有一个Person类,需要重写equals()方法来比较两个Person对象的内容是否相等:```javaOverridepublic boolean equals(Object obj) {if (this == obj) {return true;}if (obj == null || getClass() != obj.getClass()) {return false;}Person person = (Person) obj;return Objects.equals(name, )Objects.equals(age, person.age);}```3. hashCode()方法的重写实现hashCode()方法的重写时,通常需要遵循以下几个原则:3.1 使用一些非零的常数,如31等作为乘数。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

hashCode与equals的区别与联系(经典)一、equals方法的作用1、默认情况(没有覆盖equals 方法)下equals方法都是调用Object类的equals方法,而Object的equals方法主要用于判断对象的内存地址引用是不是同一个地址(是不是同一个对象)。

2 、要是类中覆盖了equals方法,那么就要根据具体的代码来确定equals方法的作用了,覆盖后一般都是通过对象的内容是否相等来判断对象是否相等。

没有覆盖equals方法代码如下:[java] view plaincopy//学生类public class Student { private int age; private String name; public Student() { } public Student(int age, String name) { super(); this.age = age; = name; } public int getAge(){ return age; } public String getName() { return name; } public void setAge(int age) { this.age = age; } public void setName(String name) { = name; } } 测试代码如下:[java] view plaincopyimport java.util.HashSet; importjava.util.LinkedList; import java.util.Set; public class EqualsTest { public static void main(String[]args) { LinkedList<Student> list = new LinkedList<Student>(); Set<Student> set = new HashSet<Student>(); Studentstu1 = new Student(3,"张三"); Student stu2 = new Student(3,"张三"); System.out.println("stu1 == stu2 : "+(stu1 == stu2));System.out.println("stu1.equals(stu2) :"+stu1.equals(stu2)); list.add(stu1);list.add(stu2); System.out.println("list size:"+ list.size()); set.add(stu1);set.add(stu2); System.out.println("set size:"+ set.size()); } } 运行结果:stu1 == stu2 : falsestu1.equals(stu2) : falselist size:2set size:2结果分析:Student类没有覆盖equals方法,stu1调用equals方法实际上调用的是Object的equals方法。

所以采用对象内存地址是否相等来判断对象是否相等。

因为是两个新对象所以对象的内存地址不相等,所以stu1.equals(stu2) 是false。

3、我们覆盖一下equals方法(age和name属性),让Student 类其通过判断对象的内容是否相等来确定对象是否相等。

覆盖后的Student类:[java] view plaincopy//学生类public class Student { private int age; private String name; public Student() { } publicStudent(int age, String name) { super();this.age = age; = name; } public int getAge() { return age; }public String getName() { return name; } public void setAge(int age) { this.age =age; } public void setName(String name){ = name; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; Student other = (Student) obj;if (age != other.age) return false;if (name == null) { if ( != null) return false; } else if (!name.equals()) return false; return true; } } 运行结果:stu1 == stu2 : falsestu1.equals(stu2) : truelist size:2set size:2结果分析:因为Student两个对象的age和name属性相等,而且又是通过覆盖equals方法来判断的,所示stu1.equals(stu2) 为true。

注意以上几次测试list和set的size都是2二、HashCode4、通过以上的代码运行,我们知道equals方法已经生效。

接下来我们在覆盖一下hashCode 方法(通过age和name属性来生成hashcode)并不覆盖equals方法,其中Hash码是通过age和name生成的。

覆盖hashcode后的Student类:[java] view plaincopy//学生类public class Student { private int age;private String name; public Student() { } public Student(int age, String name) { super(); this.age = age; = name; } public int getAge() { return age; }public String getName() { return name; } public void setAge(int age) { this.age =age; } public void setName(String name){ = name; } @Override public int hashCode() { final int prime = 31;int result = 1; result = prime * result + age; result = prime * result + ((name == null) ? 0 :name.hashCode()); return result; } } 运行结果:stu1 == stu2 : falsestu1.equals(stu2) : falselist size:2hashCode :775943hashCode :775943set size:2结果分析:我们并没有覆盖equals方法只覆盖了hashCode方法,两个对象虽然hashCode一样,但在将stu1和stu2放入set集合时由于equals方法比较的两个对象是false,所以就没有在比较两个对象的hashcode值。

5、我们覆盖一下equals方法和hashCode方法。

Student代码如下:[java] view plaincopy//学生类public class Student { private int age; private String name;public Student() { } public Student(int age, String name) { super(); this.age = age; = name; } public int getAge() { return age; } public String getName() { return name; }public void setAge(int age) { this.age =age; } public void setName(String name){ = name; } @Override public int hashCode() { final int prime = 31;int result = 1; result = prime * result + age; result = prime * result + ((name == null) ? 0 :name.hashCode());System.out.println("hashCode : "+ result); return result; } @Override public booleanequals(Object obj) { if (this == obj)return true; if (obj == null) return false; if (getClass() != obj.getClass())return false; Student other = (Student) obj;if (age != other.age) return false;if (name == null) { if ( != null) return false; } else if (!name.equals()) return false; return true; } }运行结果:stu1 == stu2 : falsestu1.equals(stu2) :truelist size:2hashCode :775943hashCode :775943set size:1结果分析:stu1和stu2通过equals方法比较相等,而且返回的hashCode值一样,所以放入set集合中时只放入了一个对象。

相关文档
最新文档