必须同时重写equals()和hashcode()方法,否则哈希表无法正确识别逻辑相等的对象;若仅重写equals()而未重写hashcode(),相同内容对象会被散列到不同桶中,导致查找不到、重复存储,违反set不重复和map键匹配的语义。

因为哈希表(如 HashMap、HashSet)依赖这个规则才能正确工作。
哈希表查找过程需要两步配合
哈希表底层是“数组 + 链表/红黑树”结构。当放入或查找一个对象时:
- 第一步:用 hashCode() 计算出它该放在哪个桶(数组下标)
- 第二步:在那个桶里,用 equals() 逐个比对,确认是不是同一个逻辑对象
如果两个对象 equals() == true,但 hashCode() 不同,它们就会被分到不同桶里。结果就是:明明是同一个逻辑对象,却查不到、去不重、存两份。
违反规则的实际后果
比如把两个内容完全相同的自定义对象加入 HashSet:
- 只重写了
equals(),没重写hashCode() - 它们的默认
hashCode()来自内存地址,大概率不同 - 集合认为这是两个不同对象,允许同时存在 → 违反了 Set “不重复”的语义
Java 规范明确要求一致性
这不是性能优化建议,而是强制契约:
-
a.equals(b) == true⇒a.hashCode() == b.hashCode()必须成立 - 反过来不成立:
hashCode()相同,equals()可以为 false(这是哈希冲突,正常且允许) - 这个规则保证了哈希集合的行为可预测、符合预期
不重写会怎样?看一个典型场景
用自定义 User 对象作 HashMap 的 key:
- 创建
user1 = new User("Alice", 25),存入map.put(user1, "admin") - 再创建
user2 = new User("Alice", 25),调用map.get(user2) - 若未重写
hashCode(),user2的哈希值和user1不同 → 查找跳到错误桶 → 返回null,即使内容一模一样
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











