我想知道为什么new Integer(i).hashCode()
或new Long(i).hashCode()
会返回i
,但当hashCode()
被某个其他对象new Double(345).hashCode()
调用时,它会返回一个随机数。为什么呢?
答案 0 :(得分:8)
因为int
的{{1}}值完全符合并完全符合Object.hashCode()
的一般合约:
hashCode的一般合约是:
每当在执行Java应用程序期间多次在同一对象上调用它时,hashCode方法必须始终返回相同的整数,前提是不修改对象上的equals比较中使用的信息。从应用程序的一次执行到同一应用程序的另一次执行,此整数不需要保持一致。
如果两个对象根据equals(Object)方法相等,则对两个对象中的每一个调用hashCode方法必须产生相同的整数结果。
如果两个对象根据equals(java.lang.Object)方法不相等,则不需要在两个对象中的每一个上调用hashCode方法必须生成不同的整数结果。但是,程序员应该知道为不等对象生成不同的整数结果可能会提高哈希表的性能。
简而言之:
如果Integer
返回equals()
并且 (但不是必需){{>},则的哈希码必须相同{ {1}}返回true
。同样通过equals()
的声明,它必须是false
。理想情况下,哈希码应该依赖于散列的所有数据。
[{1}}
的哈希码 Object.hashCode()
必须将8个字节映射到4个字节(int
的大小)。 Long
的当前实现只会返回Long
,如果它适合int
,否则它将与高32位(4字节)进行异或运行:
Long.hashCode()
[{1}}
的哈希码显然,i
的{{1}}值不符合此条件。 int
还必须将8个字节映射到4个字节。
return (int)(value ^ (value >>> 32));
将返回一个看似随机的值,因为浮点数(Double
和double
)未存储"很好地" (例如2 {'补码如Double
或Double
)在为它们保留但使用IEEE 754 binary floating point standard的字节中,所以将这8个字节映射到4(这正是实现确实)作为使用2的补码表示的Double.hashCode()
不会是有意义的数字。
float
答案 1 :(得分:7)
整数值足够好,因为它与唯一整数本身一样唯一。
double必须以某种不同的方式进行哈希处理,因为这里的哈希值必须是整数。
答案 2 :(得分:3)
因为implementation说出来了:
Returns a hash code for this Integer.
Returns:a hash code value for this object, equal to the primitive int value represented by this Integer object.
707
708 public int hashCode() {
709 return value;
710 }
答案 3 :(得分:1)
Java中的不同类型以不同方式计算哈希码,不是它们是随机的。在Long Integer和Double的情况下,哈希码是值,但在Double的情况下,它被转换为int
答案 4 :(得分:1)
这是因为hashcode()
类的Integer
方法将值返回为哈希码。
Returns a hash code for this <code>Integer</code>.
@return a hash code value for this object, equal to the
primitive <code>int</code> value represented by this
<code>Integer</code> object.
public int hashCode() {
return value;
}
hashcode()
类的Double
方法执行某些操作并返回哈希码。
Returns a hash code for this Double object. The result is the exclusive OR
of the two halves of the long integer bit representation, exactly as produced by
the method {@link #doubleToLongBits(double)}, of the primitive double value
represented by this Double object. That is, the hash code is the value of the
expression:
public int hashCode() {
long bits = doubleToLongBits(value);
return (int)(bits ^ (bits >>> 32));
}
答案 5 :(得分:1)
Integer
类&#34;框&#34;一个原始的int
值,但它有一个自己的对象引用。如果Object.equals()
声明两个相等的对象A
和B
都必须展示相同的Object.hashCode()
,那么这样的哈希码就是前int
值。
对于Double
,它的值可能会在系统之间发生变化,这就是为什么依靠不同的机制来提供哈希码是有意义的。