0

散列概念的新手,我读过 HashMap、HashTable 等使用散列,我们需要指定一个键,同时用它存储一个值

但是,由于每个对象都有一个 hashCode() 方法,java 是否在内部通过特定字段对对象使用 hashCode 来管理它(列表除外)

4

4 回答 4

2

Object.hashCode() 的javadoc回答了这个问题:

在合理可行的情况下,由 Object 类定义的 hashCode 方法确实为不同的对象返回不同的整数。(这通常通过将对象的内部地址转换为整数来实现,但 JavaTM 编程语言不需要这种实现技术。)

(强调我的)

所以不,没有额外的字段来存储 hashCode(除非某些类决定覆盖它并使用专用字段来实现它)。

并且 hashCode 不被 JVM 使用,而是被基于散列的集合(Hashtable、HashMap、HashSet,...)

于 2012-06-09T18:08:02.510 回答
2

不,hashCode() 方法用于定义一个键,用于将其与对象的实例相关联。

它用于标识对象的特定实例,并不意味着使用散列技术来管理 Java 对象。

您可以覆盖 hashCode() 方法来定义您自己的分配键的方式来标识对象的实例。

于 2012-06-09T18:09:15.457 回答
2

如果您问“Java 是否用于hashCode()对对象进行幕后管理?”,我想答案是“否”。考虑一下如果你写了一个非常糟糕的覆盖会发生什么hashCode(); 您会期望 JVM 内部结构会因此受到阻碍吗?

于 2012-06-09T18:12:14.853 回答
0
public native int hashCode();

hashCode是本机实现。但没有字段与之关联。

This is typically implemented by converting the internal address of the
object into an integer, but this implementation technique is not required
by the JavaTM programming language.

在 OpenJDK/Oracle JVM 中,计算初始哈希码的常用方法是基于第一次请求时的内存地址。对象在内存中移动,所以每次都使用地址不是一个好的选择。哈希码不是实际地址——它通常是八的倍数,不适合直接在哈希表中使用,尤其是具有两倍大小的幂。注意身份哈希码不是唯一的。

根据文档

jvmtiError GetObjectHashCode(jvmtiEnv* env, jobject object, jint* hash_code_ptr)

For the object indicated by object, return via hash_code_ptr a hash code. 
This hash code could be used to maintain a hash table of object references, 
however, on some implementations this can cause significant performance 
impacts--in most cases tags will be a more efficient means of associating 
information with objects. This function guarantees the same hash code value 
for a particular object throughout its life.
于 2012-06-09T18:15:55.367 回答