
本文讲解如何通过重写 equals() 方法,使双向链表的 search() 方法能根据 Voter 对象的 studID 属性进行查找,避免因默认引用比较导致搜索失败。
本文讲解如何通过重写 `equals()` 方法,使双向链表的 `search()` 方法能根据 `voter` 对象的 `studid` 属性进行查找,避免因默认引用比较导致搜索失败。
在使用泛型双向链表(如 DoublyLinkedList<Voter>)进行按学号搜索时,直接传入仅含 studID 的临时 Voter 对象(如 new Voter("", "", "003"))却返回 null,根本原因在于:链表的 search() 方法内部调用 currentNode.data.equals(data) 时,使用的是 Object 类默认的 equals() 实现——即内存地址比较,而非逻辑上的学号匹配。
要解决该问题,必须在 Voter 类中显式重写 equals() 方法,明确定义“两个 Voter 对象相等”的业务语义:只要 studID 相同,即视为同一人。同时,为保持契约一致性(尤其在将来可能用于哈希集合等场景),也应配套重写 hashCode() 方法。
以下是推荐的 Voter 类关键代码实现:
public class Voter {
private String username;
private String password;
private String studID;
public Voter(String username, String password, String studID) {
this.username = username;
this.password = password;
this.studID = studID;
}
// Getter methods (required for access)
public String getStudID() {
return studID;
}
@Override
public boolean equals(Object obj) {
if (this == obj) return true; // 引用相同,直接返回
if (obj == null || getClass() != obj.getClass()) return false;
Voter voter = (Voter) obj;
return studID != null ? studID.equals(voter.studID) : voter.studID == null;
}
@Override
public int hashCode() {
return Objects.hash(studID); // 仅基于 studID 生成哈希值
}
}完成上述修改后,原驱动代码即可正常工作:
List<Voter> voterList = new DoublyLinkedList<>();
voterList.add(new Voter("Alice", "password1", "001"));
voterList.add(new Voter("Bob", "password2", "002"));
voterList.add(new Voter("Charlie", "password3", "003"));
String valueSearch = "003";
Voter result = voterList.search(new Voter("", "", valueSearch));
if (result != null) {
System.out.println("Found: " + result.getUsername() + ", ID: " + result.getStudID());
} else {
System.out.println("Not found.");
}
// 输出:Found: Charlie, ID: 003⚠️ 注意事项:
- equals() 中必须先做 null 和类型检查,避免 ClassCastException 或空指针异常;
- hashCode() 必须与 equals() 保持一致:若 a.equals(b) 为 true,则 a.hashCode() 必须等于 b.hashCode();
- 若 studID 可能为 null,equals() 中需额外判空(如上所示),否则 studID.equals(...) 会抛出 NullPointerException;
- 此方案适用于“单字段精确匹配”场景;如需支持多条件(如学号+姓名组合)或模糊搜索,则应扩展 search() 方法,接受自定义谓词(Predicate)或构建专用查询接口。
通过合理重写 equals() 和 hashCode(),我们让泛型容器真正理解业务对象的“相等性”,从而让搜索逻辑既简洁又可靠。

















