Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/355.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java8HashMapBucket中使用了哪种树类型?_Java_Hashmap_Java 8 - Fatal编程技术网

Java8HashMapBucket中使用了哪种树类型?

Java8HashMapBucket中使用了哪种树类型?,java,hashmap,java-8,Java,Hashmap,Java 8,正如我在java8中所知道的,HashMap的bucket实现发生了一些变化。如果bucket size超过某个值,则列表将转换为“平衡树” 我不明白 1.Oracle JDK中使用了哪种类型的平衡树?(AVL?红黑?类似于数据库中的索引?) 2.是二叉树吗? 3.据我所知,排序是根据hashcode执行的。例如,在我的桶中,我有102个元素。100个值与hashcode的值相等12(我知道它值得,但我只需要了解这种行为),2个值与hashcode的值相等22。 如何对值执行搜索 看看实现,它看

正如我在java8中所知道的,HashMap的bucket实现发生了一些变化。如果bucket size超过某个值,则列表将转换为“平衡树”

我不明白
1.Oracle JDK中使用了哪种类型的平衡树?(AVL?红黑?类似于数据库中的索引?)
2.是二叉树吗?
3.据我所知,排序是根据hashcode执行的。例如,在我的桶中,我有102个元素。100个值与hashcode的值相等12(我知道它值得,但我只需要了解这种行为),2个值与hashcode的值相等22。
如何对值执行搜索


看看实现,它看起来像一个二叉树。更具体地说,下面的评论表明这是一棵红黑相间的树:

static final class TreeNode<K,V> extends LinkedHashMap.Entry<K,V> {
    TreeNode<K,V> parent;  // red-black tree links
    TreeNode<K,V> left;
    TreeNode<K,V> right;
    TreeNode<K,V> prev;    // needed to unlink next upon deletion
    boolean red;
    ...
}

如您所见,这类似于标准的二进制搜索树搜索。首先,他们搜索一个
TreeNode
,该TreeNode与搜索的键具有相同的
hashCode
(因为
HashMap
的单个bucket可能包含具有不同
hashCode
的条目)。然后继续执行,直到找到一个键等于所需键的
TreeNode
。如果键的类实现了
Comparable
,则二次搜索使用
compareTo
。否则,将执行更详尽的搜索。

但是如果未实现compareTo?如果JDK已经有TreeMap,那么用另一个名称创建同一个类的原因是什么?@gstackoverflow它不是同一个类。HashMap中使用的
TreeNode
是一个实现细节。当单个容器中的条目数超过某个阈值时,它应该比HashMap的单个容器的原始链表实现提供更好的性能。我的问题有点不同。为什么jdk创始人不能在HashMap中使用TreeMap而不是TreNode?@gstackoverflow您可以自己查看代码。有一个
find(inth,objectk,Class kc)
方法,它查找具有传递的hashCode(h)且其键等于k的树节点。如果它到达一个树节点,其哈希代码为所需值,但键不相等,则它要么使用compareTo(如果可用),要么在右子树中递归搜索键,如果未找到,则在左子树中搜索键。请注意,您不应依赖此行为。如果代码已经有了错误的行为(集群哈希代码),这是一种特定于实现的回退。如果您的键散列不好,但具有可比性,您也可以从一开始就使用树映射。
    /**
     * Finds the node starting at root p with the given hash and key.
     * The kc argument caches comparableClassFor(key) upon first use
     * comparing keys.
     */
    final TreeNode<K,V> find(int h, Object k, Class<?> kc) {
        TreeNode<K,V> p = this;
        do {
            int ph, dir; K pk;
            TreeNode<K,V> pl = p.left, pr = p.right, q;
            if ((ph = p.hash) > h)
                p = pl;
            else if (ph < h)
                p = pr;
            else if ((pk = p.key) == k || (k != null && k.equals(pk)))
                return p;
            else if (pl == null)
                p = pr;
            else if (pr == null)
                p = pl;
            else if ((kc != null ||
                      (kc = comparableClassFor(k)) != null) &&
                     (dir = compareComparables(kc, k, pk)) != 0)
                p = (dir < 0) ? pl : pr;
            else if ((q = pr.find(h, k, kc)) != null)
                return q;
            else
                p = pl;
        } while (p != null);
        return null;
    }