4

我正在使用HashSet添加元素并检索它们,我知道我不会按添加它们的顺序检索数据,但我想知道它发生的确切原因?

import java.util.HashSet;
import java.util.Iterator;

 public class HS {
     public static void main(String args[]) {
         HashSet h=new HashSet();
         h.add("Mayank");
         h.add("Mayank");

         h.add("Vashist");
         h.add("Dinesh");

         h.add("Vashist");

         Iterator itr=h.iterator();
         while(itr.hasNext()) {
             System.out.println(itr.next());
         }
     }
 }
4

6 回答 6

10

这只是Setjava 中的 a 合同,来自javadoc

返回此集合中元素的迭代器。返回的元素没有特定的顺序(除非这个集合是某个提供保证的类的实例)。因此,Set不需要实现 来维护值中的任何顺序。

为了返回值的顺序Set需要维护顺序。这需要速度和空间成本。

ALinkedHashSet维护插入顺序。

于 2013-06-01T16:52:10.350 回答
3

HashSet 不保留元素添加顺序。首先,它计算应该保持不变但难以预测的对象哈希码,然后使用它来选择一个桶,该桶是已选择相同桶的对象列表。由于Iterator只是迭代所有桶,迭代顺序在很大程度上是不可预测的。

如果您需要保留订单,请改用LinkedHashSet 。但是LinkedHashSet维护一个额外的链表,因此需要更多资源。

于 2013-06-01T16:50:23.937 回答
2

AHashSet使用所谓的哈希表来存储项目。

哈希表由几个放置项目的“槽”组成。决定将物品放入哪个插槽取决于该物品的哈希码,该哈希码通常与物品的自然顺序无关。

TreeSet另一方面,A根据自然顺序存储项目,这允许按顺序遍历其内容。此顺序将基于对象的自然顺序,而不是它们插入的顺序。TreeSeta和a之间的另一个区别HashSet是 aHashSet提供 O(1) 查找、插入和删除,而 aTreeSet提供O(log(n))查找、插入和删除。

LinkedHashSet通过在插入元素时构建元素之间的链接来维护项目的插入顺序。

于 2013-06-01T16:52:43.163 回答
2

因为在 HashSet 中,为每个对象计算了一个哈希值,而这个哈希值决定了容器中特定对象的数组索引。所以插入元素的顺序自然不会保留。这允许以 O(1) 的复杂度访问所需的元素,但会消耗大量内存。

http://en.wikipedia.org/wiki/Hash_table

于 2013-06-01T16:49:31.847 回答
0

来自官方文档:

该类实现了由哈希表(实际上是 HashMap 实例)支持的 Set 接口。它不保证集合的迭代顺序;特别是,它不保证订单会随着时间的推移保持不变。[...] 这个类的迭代器方法返回的迭代器是快速失败的:如果集合在迭代器创建后的任何时间被修改

于 2013-06-01T16:51:16.763 回答
0

这是订购版本:

import java.util.Set;
import java.util.Iterator;
import java.util.Collections;
import java.util.LinkedHashSet;

 public class HS {
     public static void main(String args[]) {
         Set<String> h=Collections.synchronizedSet(new LinkedHashSet<String>());
         h.add("Mayank");
         h.add("Mayank");

         h.add("Vashist");
         h.add("Dinesh");

         h.add("Vashist");

         Iterator<String> itr=h.iterator();
         while(itr.hasNext()) {
             System.out.println(itr.next());
         }
     }
 }
于 2019-01-16T18:46:00.590 回答