我有一个类,在实例化时,为其对象创建一个唯一的ID,如下所示:
public class Foo {
private final static AtomicInteger UNIQUE_ID = new AtomicInteger(0);
private final int id;
private final String name;
private final int hashcode;
public Foo(String name) {
id = UNIQUE_ID.GetAndIncrement();
this.name = name;
int result = 17;
int result = 31 * result + id;
int result = 31 * result + name.hashCode();
hashcode = result;
}
public int getInstanceID() { return id; }
现在我想实现hashCode并以这种方式等于:
public boolean equals(Object obj) {
if (obj == this)
return true;
if (!(obj instanceof Foo))
return false;
Foo other = (Foo) obj;
return other.getInstanceID == getInstanceID();
}
public int hashCode() { return hashcode; }
}
如果我只是比较那些可能与另一个Foo信息不同的任何其他字段的对象ID,那么这被认为是不好的做法吗?另外我还应该考虑哈希码函数中的每个字段还是只使用id?
答案 0 :(得分:0)
好。合同是这样的 - 如果两个对象相等,它们必须具有相同的hashCode
。你没有重写hashCode()
,所以你可以有2个相同的对象,这些对象具有不同的哈希码,这是错误的。覆盖hashcode()
以遵守合同,然后它可能就好了。
答案 1 :(得分:0)
最佳实践是以这样的方式实现hashCode函数,以便它均匀地分布集合(哈希表)中的对象。生成相同hashCode的对象将转到同一个存储桶。 hashCode函数的工作是识别存储桶。
如果你有一个错误的函数为所有人返回相同的值,那么想象这些对象都存储在一个桶中。这使得集合的工作变得困难,因为它必须遍历每个对象并对它们运行equals方法,直到找到正确的对象为止。
当你有一个好的hashCode函数时,不同的对象由不同的桶标识。因此,给定存储桶中的对象更少,这意味着需要更少的搜索。
最好使用对象的属性来唯一标识它。