11

在 Java 中,我有一个 SortedSet,它可能有 100,000 个元素。我想高效优雅地获取最后 25 个元素。我有点疑惑。

为了获得25 个元素,我将迭代并在 25 个元素之后停止。但我不知道如何以相反的顺序迭代。有任何想法吗?

SortedSet<Integer> summaries = getSortedSet();
// what goes here :-(
4

7 回答 7

15

你需要一个NavigableSet. 否则,您将不得不低效地进行操作,遍历整个SortedSet元素并将元素收集到一个Queue您一直修剪为 25 个元素的元素中。

于 2009-02-24T13:19:48.777 回答
4

SortedSet<T>的设计假设一个非常简单的迭代模型,仅向前,因此找到前 n 个条目很容易,但找到最后一个将需要通过迭代器进行昂贵的读取,以维护最后 n 个条目的窗口。

在 1.6 中添加的NavigableSet<T>解决了这个问题(并且 1.4 TreeSet 中唯一的 SortedSet 实现实现了它,因此它很可能成为您的替代品)。

NavigableSet<T> set = new TreeSet<T>();
// add elements
set.descendingIterator() // iterate over the last n entires as needed
于 2009-02-24T13:27:24.793 回答
3

反转您的排序并获取前 25 个项目。然后,您可以将那些将是有效的,因为它只有 25 个项目。

布鲁斯

于 2009-02-24T18:25:36.030 回答
1

不同的数据结构将更适合此操作。

这不是一种优雅的方式或非常有效的方式,但假设 SortedSet 是按升序排列的,您可以获得 Last() 项并将其删除,将其存储在另一个列表中,然后重复 25 次。然后,您将不得不再次将这些元素放回去!

于 2009-02-24T13:22:18.957 回答
1

将 Set 放入 List 并使用 subList()。我不确定创建列表的性能如何,因此您必须运行一些测试。不过,它肯定会使编码变得容易。

    List f = new ArrayList( summaries);
    List lastTwentyFive = f.subList( summaries.size() - 25, summaries.size() );
于 2009-02-24T16:48:37.650 回答
1

https://github.com/geniot/indexed-tree-map

您可能想看看IndexedTreeMap in indexed-tree-map

使用exact(size-25) 无需迭代即可到达索引处的元素。

于 2014-01-27T13:40:27.600 回答
0

我假设这在您的项目中不太可能有任何实际用途,但值得注意的是,您可能只是能够将列表按相反方向排序:)

于 2009-02-24T14:40:04.120 回答