HashSet与JDK 7/8的顺序和区别 [英] HashSet order and difference with JDK 7 / 8

查看:231
本文介绍了HashSet与JDK 7/8的顺序和区别的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是一个由两部分组成的问题:

This is a two part question:


  1. HashSet是否实现了一些隐藏的排序机制,或者只是引用文档:它不保证集合的迭代顺序;特别是,它并不保证订单会随着时间的推移保持不变。告诉我订单有时可能会在未来发生变化和/或取决于内存使用情况吗?

  2. 当我在JDK之间切换时,为什么我会完全不同'订购'(我敢说)?

  1. Does HashSet implement some hidden ordering mechanic or it just, to quote the documentation:It makes no guarantees as to the iteration order of the set; in particular, it does not guarantee that the order will remain constant over time. tells me that the order MIGHT change sometimes in the future and/or depending on memory usage?
  2. Why am I getting completely different 'ordering' (dare I say) when I switch between JDKs?

举个例子:

for (int i = 0; i < 1000; i++) {
        Set<String> stringSet = new HashSet<>();
        stringSet.add("qwe");
        stringSet.add("rtz");
        stringSet.add("123");
        stringSet.add("qwea");
        stringSet.add("12334rasefasd");
        stringSet.add("asdxasd");
        stringSet.add("arfskt6734");
        stringSet.add("123121");
        stringSet.add("");
        stringSet.add("qwr");
        stringSet.add("rtzz");
        stringSet.add("1234");
        stringSet.add("qwes");
        stringSet.add("1234rasefasd");
        stringSet.add("asdxasdq");
        stringSet.add("arfskt6743");
        stringSet.add("123121 ");
        stringSet.add(" ");
        System.out.println(stringSet);
    }

无论我运行多少次,都会产生以下输出:

will, no matter how many times I run it, produce the following output:

JDK 7: [,, 123,qwea,asdxasdq,qwe,qwr,123121,arfskt6743,1234rasefasd,qwes,rtz,rtzz,1234 ,12334rasefasd,asdxasd,arfskt6734,123121]

JDK 8: [,, qwes,arfskt6743,asdxasdq,123121 ,123121,arfskt6734,qwr,123,1234,qwea,rtzz,rtz,12334rasefasd,1234rasefasd,qwe,asdxasd]

显然,空字符串和whitespace-only-string两次都是引导方式,但其余部分完全不同。

Obviously, the empty string and the whitespace-only-string are leading the way both times, but the rest of it is completely different.

推荐答案

根据收集更新更改页面


7u6中添加的备用String散列函数已从JDK 8中删除,同时还有jdk.map.althashing.th保留系统财产。相反,包含大量冲突键的哈希箱通过将其条目存储在平衡树而不是链表中来提高性能。此JDK 8更改仅适用于HashMap,LinkedHashMap和ConcurrentHashMap。

The alternative String hash function added in 7u6 has been removed from JDK 8, along with the jdk.map.althashing.threshold system property. Instead, hash bins containing a large number of colliding keys improve performance by storing their entries in a balanced tree instead of a linked list. This JDK 8 change applies only to HashMap, LinkedHashMap, and ConcurrentHashMap.

在极少数情况下,此更改可能会引入对HashMap和HashSet的迭代顺序的更改。没有为HashMap对象指定特定的迭代顺序 - 任何依赖于迭代顺序的代码都应该是固定的。

In rare situations, this change could introduce a change to the iteration order of HashMap and HashSet. A particular iteration order is not specified for HashMap objects - any code that depends on iteration order should be fixed.






所以,基本上

用于散列集合的算法已更改为改善性能。它变为平衡树而不是链表。

The Algorithm for hashing your set has changed to improve performance. It changed to a balanced tree instead of a linked list.

这种变化可能会改变你的集合的迭代顺序,并确定这种行为应该由你,如果你依赖它。

This kind of change might change the iteration order of your set, and it's established that this kind of behavior should be fixed by you, if you depend upon it.

你看到你的套装有更好的实现,看起来可能是有序的,但这纯属巧合。

You're seeing a better implementation of your set, which might look like it's ordered, but it's pure coincidence.

我建议你不要依赖套装的迭代订单,因为订单不是保证。

I would recommend you to not rely on the iteration order for sets, as the order is not a guarantee.

@Edit

另一个概念也很重要,如用户Holger所述,

Another concept is also important, as stated by user Holger,


默认情况下不使用Java 7的替代字符串散列函数。此外,平衡树仅适用于桶冲突场景。尽管如此,由于这种改进,还有另一个未提及的变化。对象的哈希码到数组位置的映射经历了从Java 7简化到Java 8的转换

The "alternative String hash function" of Java 7 was not used by default. Further, the balanced tree only applies to bucket collision scenarios. Still, as a consequence of this improvement, another, unmentioned change has been made. The mapping of an object’s hashcode to an array position undergoes a transformation which has been simplified from Java 7 to Java 8

这篇关于HashSet与JDK 7/8的顺序和区别的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆