JavahashCode()方法
示例
当Java类覆盖该equals方法时,它也应覆盖该hashCode方法。根据方法合同中的定义:
在Java应用程序执行期间,只要在同一对象上多次调用它,该hashCode方法就必须一致地返回相同的整数,前提是不修改该对象的equals比较中使用的信息。从一个应用程序的执行到同一应用程序的另一执行,此整数不必保持一致。
如果根据该equals(Object)方法两个对象相等,则hashCode在两个对象中的每个对象上调用该方法必须产生相同的整数结果。
如果两个对象根据该equals(Object)方法不相等,则不需要在两个对象中的hashCode每一个上调用该方法必须产生不同的整数结果。但是,程序员应该意识到,为不相等的对象生成不同的整数结果可能会提高哈希表的性能。
散列码在散列实现,如使用HashMap,HashTable,和HashSet。该hashCode函数的结果确定将放置对象的存储桶。如果提供的hashCode实现良好,则这些哈希实现效率更高。良好hashCode实现的重要属性是hashCode值的分布是均匀的。换句话说,将多个实例存储在同一存储桶中的可能性很小。
用于计算哈希码值的算法可能类似于以下内容:
public class Foo { private int field1, field2; private String field3; public Foo(int field1, int field2, String field3) { this.field1 = field1; this.field2 = field2; this.field3 = field3; } @Override public boolean equals(Object obj) { if (this == obj) { return true; } if (obj == null || getClass() != obj.getClass()) { return false; } Foo f = (Foo) obj; return field1 == f.field1 && field2 == f.field2 && (field3 == null ? f.field3 == null : field3.equals(f.field3); } @Override public int hashCode() { int hash = 1; hash = 31 * hash + field1; hash = 31 * hash + field2; hash = 31 * hash + (field3 == null ? 0 : field3.hashCode()); return hash; } }
使用作为一个捷径Arrays.hashCode()
在Java1.2及更高版本中,代替开发一种算法来计算哈希码,可以java.util.Arrays#hashCode通过提供一个包含字段值的Object或基本数组来生成一个:
@Override public int hashCode() { return Arrays.hashCode(new Object[] {field1, field2, field3}); }
Java1.7引入了java.util.Objects提供便捷方法的类,该类hash(Object...objects)根据提供给它的对象的值计算哈希码。此方法的工作方式与相同java.util.Arrays#hashCode。
@Override public int hashCode() { return Objects.hash(field1, field2, field3); }