【发布时间】:2020-09-22 14:47:45
【问题描述】:
我有一个名为 Department 的自定义类,其中 equals 和 hashCode 都被覆盖了。请找到如下的sn-p:
class Department {
private final int id;
private final String name;
private final int count;
public Department(int id, String name, int count) {
super();
this.id = id;
this.name = name;
this.count = count;
}
@Override
public boolean equals(Object obj) {
if (obj == null)
return false;
if (!(obj instanceof Department))
return false;
final Department emp = (Department) obj;
return emp.name != null && emp.name.equals(name) && emp.count == count && emp.id == id;
}
@Override
public int hashCode() {
return count + name.length();
}
@Override
public String toString() {
return "ID: " + id + ", Name: " + name + ", Age: " + count + ", hashCode: " + hashCode();
}
}
在 main 方法中,我以这样的方式初始化了两个部门,它们的 equals 将返回 false 但具有相同的哈希码。然后将这两个部门添加到 HashMap 中。请找到以下主要方法调用:
public static void main(String[] args) {
final Department dep1 = new Department(1, "software", 35);
final Department dep2 = new Department(2, "software", 35);
System.out.println("\n\nIs dep1.equals(dep2)? -- " + dep1.equals(dep2));
System.out.println("Is dep1==dep2? -- " + (dep1 == dep2));
System.out.println("\n\nDepartment 1: " + dep1);
System.out.println("Department 2: " + dep2);
final HashMap<Department, String> departmentHashMap = new HashMap<>();
departmentHashMap.put(dep1, "Software 1");
System.out.println("\n\nDepartment 1 added to map");
System.out.println("Is Department 2 available in map? -- " + departmentHashMap.get(dep2));
System.out.println("Is Department 2 key available in map? -- " + departmentHashMap.containsKey(dep2));
departmentHashMap.put(dep2, "Software 2");
System.out.println("\n\nDepartment 1: " + departmentHashMap.get(dep1));
System.out.println("Department 2: " + departmentHashMap.get(dep2));
for (final Entry<Department, String> entry : departmentHashMap.entrySet()) {
System.out.println("Key: " + entry.getKey() + ", Value: " + entry.getValue());
}
}
根据文档,当两个不同的条目具有相同的hashcode但不满足equals比较时,会导致HashMap发生冲突,条目将存储为链表。我没有观察到这种特殊行为。但是当我遍历 HashMap 条目时,它们被作为单独的条目获取,而不是链表。请找到如下输出:
Is dep1.equals(dep2)? -- false
Is dep1==dep2? -- false
Department 1: ID: 1, Name: software, Age: 35, hashCode: 43
Department 2: ID: 2, Name: software, Age: 35, hashCode: 43
Department 1 added to map
Is Department 2 available in map? -- null
Is Department 2 key available in map? -- false
Department 1: Software 1
Department 2: Software 2
Key: ID: 1, Name: software, Age: 35, hashCode: 43, Value: Software 1
Key: ID: 2, Name: software, Age: 35, hashCode: 43, Value: Software 2
我无法在任何地方引用举例说明这种特殊情况。任何有助于澄清概念的帮助都将受到高度赞赏。
【问题讨论】:
-
请链接“文件”! “实施的真相”可以在source code 中找到。当然所有“冲突注意事项”都是“内部的”,不会影响外部 api (
entrySet()) -
在内部,它存储键/值对。因此,当发生碰撞时,它们会被添加到同一个存储桶中的“列表”中。迭代此列表以找到适当的匹配键,以便使用与其关联的值。换句话说,在地图之外,没有“LinkedList”机制的概念,这是一个被封装的实现细节。
标签: java hashmap equals hashcode