当前位置: 首页 > news >正文

厦门的服装商城网站建设正版seo搜索引擎

厦门的服装商城网站建设,正版seo搜索引擎,wordpress别人主题插件,网络运维工程师是做什么的文章目录 一、什么是equals()二、什么是hashCode()三、hashCode是如何得到的1. 类重写了hashCode()2. 类没有重写hashCode() 四、总结1. hashCode()和equals()的比较2. 为何hashCode()和equals()搭配使用比较对象时能提高效率 一、什么是equals() 我们先来看下再熟悉不过的equ…

文章目录


一、什么是equals()

我们先来看下再熟悉不过的equals方法。以下是java api对equals()方法的说明:
在这里插入图片描述
从上面关于equals的说明,我们可以得出以下几点:

  1. equals用来判断两个对象是否相等。在判断时分为两种情况:
    1.1 对象所属类没有重写该方法,这时比较的是对象的地址,即引用是否相等。
    1.2 对象所属类重写了该方法,这时比较的是对象的内容,即对象内容相同时,equals就返回true。

  2. 重写了equals方法时,必须重写hashCode方法,以便遵守hashCode方法的规则(相等的对象必须具有相等的哈希码)。

二、什么是hashCode()

hashCode()是Object类中定义的一个方法。以下是java api对hashCode方法的说明:
在这里插入图片描述我们可以看出以下几点:

  1. hashCode方法返回的是对象的哈希值。支持该方法是为哈希表提供一些优点,例如,java.util.Hashtable 提供的哈希表。其实是为了提高查找效率,hashCode的主要作用就是用来在散列存储结构中确定对象的存储地址的。
  2. 同一对象的哈希值唯一。
  3. 若使用equals(Object)方法比较的两个对象相等,则这两个对象的哈希值相等。
  4. 若使用equals(Object)方法比较的两个对象不相等,则这两个对象的哈希值也可能相等。
  5. equals返回true时,哈希值一定相等;而哈希值相等时,equals返回值不确定,即对象不一定相等

也就是说任何类中实现的hashCode方法都需要遵守这些规则,其实就是上面的第5点。那么,为什么equals返回true时,哈希值一定相等呢?而哈希值相等时,equals返回值反而不确定呢?hashCode又是如何得到的呢?实践出真知,下面我们从源码和案例的角度来看下。

三、hashCode是如何得到的

1. 类重写了hashCode()

  • hashCode返回的是一个整数,可以通过它得到在散列存储结构中,这个对象的存储地址。比如HashSet中就是根据hashcode再计算得到元素在底层数组中的位置的。

  • 以下我们先创建一个重写了equals和hashCode方法的Person类:
import java.util.Objects;public class Person {private String name;private int age;public Person(String name, int age) {this.name = name;this.age = age;}@Overridepublic String toString() {return "Person{" +"name='" + name + '\'' +", age=" + age +'}';}@Overridepublic boolean equals(Object o) {if (this == o) return true;if (o == null || getClass() != o.getClass()) return false;Person person = (Person) o;return age == person.age &&Objects.equals(name, person.name);}@Overridepublic int hashCode() {return Objects.hash(name, age);}
}
  • 以下是测试类
public class HashCodeTest {public static void main(String[] args) {Person person1 = new Person("Tom", 12);Person person2 = new Person("Tom", 12);Person person3;person3 = person1;String str = "a";Integer num1 = 97;System.out.println(str.hashCode() + " " + num1.hashCode());//说明hashcode相等,equals不一定相等System.out.println(person1.hashCode() + " " + person2.hashCode());System.out.println(person3.hashCode() == person1.hashCode());//true,因为内存地址一样}
}
  • 以下是输出结果
97 97
2613467 2613467
true
  • 首先对于str对象和num1对象,为什么他们的哈希值相等呢?我们可以分别看一下String类和Integer类中对hashCode的实现。首先是String类中关于hashCode()的源码:
/*** Returns a hash code for this string. The hash code for a* {@code String} object is computed as* <blockquote><pre>* s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1]* </pre></blockquote>* using {@code int} arithmetic, where {@code s[i]} is the* <i>i</i>th character of the string, {@code n} is the length of* the string, and {@code ^} indicates exponentiation.* (The hash value of the empty string is zero.)** @return  a hash code value for this object.*/public int hashCode() {int h = hash;final int len = length();if (h == 0 && len > 0) {for (int i = 0; i < len; i++) {h = 31 * h + charAt(i);}hash = h;}return h;}
  • 可以看出,String中生成对象的哈希码主要是依据字符串对象中的每个字符计算出来的。
  • 从下面Integer类中hashCode的源码可以看出,它是直接将Integer对象的值作为哈希值的。所以上面例子中str和num1的哈希值都是97。而如果用equals对它们进行比较,肯定返回false。这就证明了哈希值相等时,对象不一定相等。
@Overridepublic int hashCode() {return Integer.hashCode(value);}/*** Returns a hash code for a {@code int} value; compatible with* {@code Integer.hashCode()}.** @param value the value to hash* @since 1.8** @return a hash code value for a {@code int} value.*/public static int hashCode(int value) {return value;}
  • 那么对于对象person1和person2,为什么他们的哈希值也相等呢?我们先看下Person类重写的hashCode的方法的底层源码:
public static int hash(Object... values) {return Arrays.hashCode(values);}
public static int hashCode(Object a[]) {if (a == null)return 0;int result = 1;for (Object element : a)result = 31 * result + (element == null ? 0 : element.hashCode());return result;}

它与上面String类中hashCode的实现原理类似,都是根据对象里的每个属性计算得到,也是将素数31作为乘法器。因此,由于person1和person2的内容相同,它们的哈希值也就是一样的了。而且这时也是遵守hashCode的规则的,因为Person类重写了equals方法,所以此时用equals比较这两个对象,仍然是相等的。这就证明了equals相等,hashCode一定相等。当然前面所有观点成立的前提都是类中重写了hashCode()和equals()。

2. 类没有重写hashCode()

  • 那么如果类中没有重写hashCode方法呢,这时hashcode又是如何生成的呢?
import java.util.Objects;public class Person {private String name;private int age;public Person(String name, int age) {this.name = name;this.age = age;}@Overridepublic String toString() {return "Person{" +"name='" + name + '\'' +", age=" + age +'}';}    
}
  • 我们将例子中重写的hashCode方法和equals方法去除,得到的Person类如上所示。这时得到的哈希值和上面的不一样了:
97 97
1163157884 1956725890
true
  • 实际上, 当 自 定 义 类 没 重 写 h a s h C o d e ( ) 时 , 哈 希 值 是 根 据 对 象 在 内 存 中 的 地 址 生 成 的 \color{red}{当自定义类没重写hashCode()时,哈希值是根据对象在内存中的地址生成的} hashCode()。从下面的源码看出,对象调用的是Object类的原生的hash方法,然后在hash方法中再调用系统的identityHashCode方法来生成哈希值,identityHashCode方法永远返回根据对象物理内存地址产生的hash值,所以由于person1和person2对象的物理地址不一样,最后生成的哈希值也会不一样。
// public native int hashCode();
public int hashCode() {return identityHashCode(this);}// Package-private to be used by j.l.System. We do the implementation here// to avoid Object.hashCode doing a clinit check on j.l.System, and also// to avoid leaking shadow$_monitor_ outside of this class./* package-private */ static int identityHashCode(Object obj) {int lockWord = obj.shadow$_monitor_;final int lockWordStateMask = 0xC0000000;  // Top 2 bits.final int lockWordStateHash = 0x80000000;  // Top 2 bits are value 2 (kStateHash).final int lockWordHashMask = 0x0FFFFFFF;  // Low 28 bits.if ((lockWord & lockWordStateMask) == lockWordStateHash) {return lockWord & lockWordHashMask;}return identityHashCodeNative(obj);}

我们可以做一下验证。如果在测试类中添加以下内容,会发现它和person1.hashCode()的结果是相同的。

System.out.println(System.identityHashCode(person1));

四、总结

1. hashCode()和equals()的比较

  • 当类重写它们时,hashCode()返回的是根据对象的内容(属性)计算出的一个整数;equals()判断的是对象的内容是否相等。
  • 比较两个对象是否相等时,hashCode()相等,equals()不一定相等,因此不可靠; e q u a l s ( ) 相 等 时 , h a s h C o d e ( ) 一 定 相 等 \color{red}{ equals()相等时,hashCode()一定相等} equals()hashCode()

2. 为何hashCode()和equals()搭配使用比较对象时能提高效率

  • 当成员变量很多时, 只 用 e q u a l s ( ) 比 较 , 方 法 内 部 会 涉 及 大 量 的 操 作 \color{red}{ 只用equals()比较,方法内部会涉及大量的操作} equals(),效率低,所以可以先判断hashCode()值,若不相等,则对象肯定不相等;否则继续用equals()判断。
http://www.ds6.com.cn/news/14617.html

相关文章:

  • 怎样用自己的电脑,做网站网络营销课程
  • 网站建设主机配置搜索引擎seo优化平台
  • 可以在手机建网站的推广一般去哪发帖
  • 动画制作学什么专业重庆seo技术教程博客
  • php学完可以做网站东莞关键词排名快速优化
  • 新兴县做网站的seo关键词有话要多少钱
  • 网站内部链接有什么作用免费网站统计代码
  • 游戏网站建设毕业论文系统优化大师官方下载
  • 郑州网站建设 郑州网站制作搜索引擎营销的主要模式
  • 专业h5网站制作百度搜索数据查询
  • 中文网站建设翻译成英文是什么意思网站推广 方法
  • 志愿者管理网站开发的需求分析 基于 java关键词分类
  • 深圳网站制作公司讯息优化关键词的正确方法
  • 注册做网站的公司网站关键词收录查询
  • 刷东西的网站自己做百家号关键词seo优化
  • 怎么做汽车网站常熟网络推广
  • 建网站 西安怎么注册自己的网站
  • 北碚网站建设公司网络运营培训课程
  • 做js题目的网站合肥网站排名推广
  • 炫的手机网站研究生培训机构排名
  • 512内存服务器做网站seo学习网站
  • 北京网站建设新闻鞍山seo公司
  • 链接测试对于网站的意义广告公司图片
  • 做钓鱼网站盗游戏号会被判刑吗宁波seo快速排名
  • 网站建设公司 上营销策略分析包括哪些内容
  • 查看网站是否做百度推广如何制作网页最简单的方法
  • 做飞机票的图片的网站职业技能培训
  • 如何改善网站网站自然优化
  • 湖北省建设厅招骋网站电商seo是什么
  • 天津企业做网站哈尔滨最新疫情