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

equals()与hashCode()之间的关系

目录

概述

equals 方法

hashCode 方法

为什么必须同时重写equals()与hashCode()

拓展 :HashMap 与 HashSet 的区别


概述

  • 概述:equals 与 hashCode 是 Java 中的 Object 类的两个核心方法,主要用于对象比较哈希表操作,两者之间紧密关联,equals 与 hashCode 是 Java 中必须共同遵守的一个约定,正确实现它们,可以确保 HashMap、HashSet 等哈希集合正常工作。

  • Object 常见方法

{    // 返回此对象的运行时类public final native Class<?> getClass();// 返回对象的哈希码值public native int hashCode();// 判断两个对象是否相等public boolean equals(Object obj) {return (this == obj);}// 创建并返回此对象的一个副本protected native Object clone() throws CloneNotSupportedException;// 返回对象的字符串表示public String toString() {return getClass().getName() + "@" + Integer.toHexString(hashCode());}// 唤醒在此对象监视器上等待的单个线程public final native void notify();// 唤醒在此对象监视器上等待的所有线程public final native void notifyAll();// 让当前线程等待,直到另一个线程调用此对象的notify()或notifyAll()方法public final native void wait(long timeout) throws InterruptedException;// 带纳秒精度的wait方法public final void wait(long timeout, int nanos) throws InterruptedException // 无限期等待public final void wait() throws InterruptedException // 当垃圾回收器确定不存在对该对象的更多引用时,由对象的垃圾回收器调用此方法protected void finalize() throws Throwable { }
}

equals 方法

  • 基本概述: equals 用于判断两个对象的内容是否相等,即逻辑相等性而不是物理地址相等,同时不能判断基本数据类型的变量,Object 类默认情况下,equals 等价于==,即比较的是内存地址,所以实际业务中,我们需要对 equals 方法进行重写操作。

  • object 类中默认实现

public boolean equals(Object obj) {return (this == obj); // 比较两个对象的内存地址(即物理地址)
}

hashCode 方法

  • 基本概述:hashCode 主要是可以将数据通过一个算法映射成一个固定大小的值,即哈希值,主要用于哈希表(例如 HashMap、HashSet 等哈希集合)快速定位对象存储位置的,提高查询效率。

  • object 类中默认实现

public native int hashCode(); // 本地方法,通常根据对象的内存地址计算哈希码

为什么必须同时重写equals()与hashCode()

首先要知道两个相等的对象 hashCode 值必须相等,Object 类是 Java 中所有类的终极父类,默认情况下 hashCode 是基于内存地址计算的,且默认情况下 equals 也是与==等价的,如果重写了 equals 而没有重写 hashCode,那么在判断两个对象是否相等时,a.equals(b)为 true但是因为hashCode 默认情况下是基于内存地址计算,最终因不同地址而返回不同的值因此 a.hashCode() 与 b.hashCode()不相等,这直接违反了 Java 的核心约定(equals 为 true 的对象,hashCode 必须相等)。这种违反约定的行为,在使用哈希表相关集合(HashMap、HashSet、LinkedHashMap等)时会引发致命问题。例如可能 HashMap 中明明存在某数据,但因违反约定,而查找失效;

不同时重写导致问题的例子

  • 当你把两个逻辑相等的对象存入 HashSet时,HashSet会先通过 hashCode 计算存储位置(“桶”):由于两者 hashCode 不同,会被分配到不同的桶中,后续即使通过 equals 判断是同一个对象,也不会被视为重复元素,最终导致 HashSet 中出现重复数据(违背去重特性)。

  • 当你用逻辑相等的对象作为 HashMap 的 key 查找或存入时,同样会因为 hashCode 不同,无法定位到同一个桶,导致无法找到已存入的键值对(查找失效),或重复存入相同逻辑的 key(破坏 key 唯一性)。

  • 即使是遍历哈希表,也可能因为对象的 hashCode 与 equals 逻辑不匹配,出现遍历结果混乱、元素丢失等问题。

总之

  • 如果 a.equals(b) == true,则 a.hashCode() == b.hashCode() 必须成立
  • 反之,如果 a.hashCode() == b.hashCode()a.equals(b) 可以返回 false(允许哈希冲突)。

拓展 :HashMap 与 HashSet 的区别

特性

HashMap

HashSet

实现接口

Map接口

Set接口

存储内容

键值对

仅存储对象,且实际上,这个对象作为HashMap的键

重复元素

不允许重复的键,但允许重复的值

不允许任何重复的元素

空值处理

允许null作为键和值

允许为null

添加方法

put(K key,V value)

add(E e)

内部实现

它本身就是一个哈希表,存储 Entry

内部使用了一个HashMap,你添加的元素被用作这个内部HashMap的,而值则是一个固定的虚拟对象

操作方式

使用 get(key)通过来获取值

使用 contain(e)检查元素是否存在

  • 小结HashSet是基于HashMap实现的,当你向 HashSet 添加一个元素时,实际上是将这个元素作为放入了一个内部的 HashMap 中,而对应的则是一个固定的、无意义的对象。正因为 HashMap 的键是唯一的,所以 HashSet 天然地保证了元素的唯一性。

结尾

        Java 中 equals 与 hashCode 的设计,本质是 “逻辑相等定义” 与 “哈希存储优化” 的协同 —— 前者明确对象 “是否相同”,后者为集合提供 “快速定位” 的基础,而 HashMap 与 HashSet 则是这种协同设计的典型应用。

        实际开发中,我们无需手动编写复杂的重写逻辑(可通过 Lombok 的 @EqualsAndHashCode 注解自动生成,确保规范),但必须牢记核心约定:重写 equals 必重写 hashCode,且两者基于相同的关键属性实现

        这些基础概念看似简单,却直接影响代码的正确性与性能 —— 比如忽略约定会导致 HashSet 去重失效、HashMap 查找异常,这些问题在线上环境中往往难以排查。因此,夯实这些底层逻辑,不仅能避免初级错误,更能帮助我们理解集合、框架的设计思想,为后续深入学习打下坚实基础。希望本文能让你对这些核心概念的理解更透彻。

http://www.dtcms.com/a/565188.html

相关文章:

  • Visual Studio Code 控制台乱码问题
  • 网站实现中英文asp.net网站很快吗
  • 公司网站链接建设电影网站论文
  • nvm切换node版本时,npm不跟着切换解决
  • iOS 应用逆向对抗手段,多工具组合实战(iOS 逆向防护/IPA 混淆/无源码加固/Ipa Guard CLI 实操)
  • x86架构的Ubuntu 22系统上,备份ISO镜像
  • 死锁防范:四大条件与破解之道
  • 考研408--数据结构--day1--基础概念时间、空间复杂度
  • 网站建设服务标准自己做热图的网站
  • WordPress如何设置站点名称做摄影网站的目的
  • Git创建合并分支、多人协作
  • 怎么做地下彩票网站郑州做网站那家做的好
  • 网站这么做项目ppt制作模板
  • 有什么做logo网站淮北矿业集团工程建设公司网站
  • 基于springboot的大型商场应急预案管理系统
  • 凌恩又升级内容啦!160+项分析!
  • 安装 Conda 并配置 LLM 开发环境
  • 网站建设淘宝好评注册岩土工程师
  • 小说网站开发中遇到的问题网站保护等级是企业必须做的么
  • /tmp/jave/ffmpeg-amd64-2.4.6-SNAPSHOT 的生成者和生成原因
  • 基础开发工具--编译器g++/gcc 自动化构建make/Makefile
  • Linux 常用命令速查
  • npj Digital Medicine|单细胞 × 空间 × 去卷积:乳腺癌基质-免疫生态的图谱分析与ICB 悖论
  • Docker爆红且安装非C盘处理方案
  • NAS/SAN存储:NFS/iSCSI/FC 存储协议与应用场景
  • 基于张祥前统一场论的太空中引力确定方法研究
  • 【会议征稿】第二届环境工程、城市规划与设计国际学术会议(EEUPD 2025)
  • 上外网看新闻去哪个网站创建目录wordpress
  • 双星开源:Astron-Agent 与 Astron-RPA 在 GitCode 上线,加速 AI 智能体时代!
  • 网站建设推广公司需要哪些岗位wordpress的缩略图无法显示