我相信有一个很好的理由,但有人能解释一下为什么java.util.Set接口缺少get(int Index),或任何类似的get()方法吗?

集合似乎很适合把东西放进去,但我找不到一种优雅的方法来从中检索单个项目。

如果我知道我想要的第一项,我可以使用set.iterator().next(),但否则,似乎我必须强制转换到一个数组来检索特定索引的项?

从集合中检索数据的适当方法是什么?(与使用迭代器不同)

我相信它被排除在API之外的事实意味着有一个很好的理由不这样做——有人能启发我吗?

编辑: 这里有一些非常棒的回答,还有一些说“更多的背景”。具体的场景是一个dbUnit测试,在这个测试中,我可以合理地断言从查询返回的集合只有1个项,并且我正在尝试访问该项。

然而,这个问题在没有场景的情况下更有效,因为它仍然更集中:

set和list的区别是什么?

感谢大家的精彩回答。


当前回答

请注意,只有2个基本的数据结构可以通过索引访问。

数组数据结构可以通过O(1)时间复杂度的索引访问,实现get(int index)操作。 LinkedList数据结构也可以通过索引访问,但要用O(n)时间复杂度来实现get(int index)操作。

在Java中,ArrayList是使用Array数据结构实现的。

而Set数据结构通常可以通过HashTable/HashMap或BalancedTree数据结构实现,为了快速检测元素是否存在并添加不存在的元素,通常一个实现良好的Set可以实现O(1)个时间复杂度包含操作。在Java中,HashSet是Set最常用的实现,它是通过调用HashMap API来实现的,HashMap是使用链表(Array和LinkedList的组合)来实现的。

由于Set可以通过不同的数据结构实现,因此没有get(int index)方法。

其他回答

我能想到的在集合中使用数值索引的唯一原因是为了迭代。为此,请使用

for(A a : set) { 
   visit(a); 
}

这就引出了一个问题,什么时候应该使用集合,什么时候应该使用列表。通常,建议是这样的:

如果需要有序数据,请使用List 如果你需要唯一的数据,使用一个集合 如果两者都需要,可以使用SortedSet(用于按比较器排序的数据)或OrderedSet/UniqueList(用于按插入排序的数据)。不幸的是,Java API还没有OrderedSet/UniqueList。

第四种经常出现的情况是,两者都不需要。在这种情况下,你会看到一些程序员使用列表,一些使用集合。就我个人而言,我觉得把set看作一个没有顺序的列表是非常有害的——因为它真的是另一种野兽。除非你需要集唯一性或集相等性,否则总是倾向于列表。

因为Set在随机位置存储唯一的元素,并且在内部它使用多个数据结构。即数组,链表,带有哈希的树。

链接 https://en.wikipedia.org/wiki/Set_ (abstract_data_type)

根据Set集合的定义,Set中的元素是无序的。所以它们不能被索引访问。

但是为什么我们没有一个get(object)方法,不是通过提供索引作为参数,而是提供一个与我们正在寻找的对象相等的对象? 通过这种方式,我们可以访问Set中元素的数据,只需要知道equal方法使用的属性。

只是补充一点迈尔斯的回答中没有提到的。

如果我知道我想要第一项,我就可以 使用set.iterator().next(),但是 不然的话,我只好放弃了 数组中检索项 具体指标? 合适的方式是什么 从集合中检索数据?(其他 而不是使用迭代器)

您还应该熟悉SortedSet接口(其最常见的实现是TreeSet)。

SortedSet是一个集合(即元素是唯一的),它通过元素的自然顺序或使用一些比较器保持有序。可以使用first()和last()方法轻松访问第一个和最后一个项。SortedSet每隔一段时间就会派上用场,当您需要保持集合无重复且以某种方式有序时。

编辑:如果你需要一个Set,它的元素按照插入顺序保存(很像List),看一下LinkedHashSet。