如何有效地跟踪集合中的最小元素?

时间:2008-08-29 04:54:09

标签: data-structures collections

编程问题中:假设有一组对象可以相互比较和排序。在添加对象时,跟踪集合中最小元素的最有效方法是什么?偶尔删除当前最小元素?

7 个答案:

答案 0 :(得分:6)

使用最小堆是最好的方法。

http://en.wikipedia.org/wiki/Heap_(data_structure)

这是为这个应用量身定做的。

答案 1 :(得分:1)

如果需要随机插入和删除,最好的方法可能是排序数组。插入和删除应为O(log(n))。

答案 2 :(得分:1)

@Harpreet
这不是最佳的。删除对象后,erickson必须扫描整个集合才能找到新的最小值。

您想阅读Binary search tree的内容。 MS有一个很好的site来开始这条路。但是如果你想深入了解,你可能想得到像Introduction to algorithms (Cormen, Leiserson, Rivest, Stein)这样的书。

答案 3 :(得分:1)

对于偶尔删除,Fibonacci Heap甚至比最小堆快。插入是O(1),找到min也是O(1)。删除是O(log(n))

答案 4 :(得分:0)

  

如果您需要随机插入和移除,   最好的方法可能是排序   阵列。插入和删除应该是   为O(log(N))。

是的,但您需要对每个插入和(可能)每次删除进行重新排序,如您所述,这是O(log(n))。

使用Harpreet提出的解决方案:

  • 你在开头有一个O(n)传球来找到最小的元素
  • 此后
  • 插入是O(1)(只需要对已知的最小元素进行1次比较)
  • 删除将是O(n),因为您需要重新找到最小元素(请记住Big O表示法是最坏的情况)。您还可以通过检查要删除的元素是否(已知)最小来进行优化,如果不是,则不要进行任何重新检查以找到最小元素。

所以,这取决于。这些算法中的一种对于具有少量删除的插入大用例更好,但另一种更总体上更一致。我想我会默认使用Harpreet的机制,除非我知道经常删除最小的数字,因为这暴露了该算法的弱点。

答案 5 :(得分:0)

Harpreet:

  

插入到该列表中将是线性的,因为您必须移动插入项目。

这不取决于集合的实现吗?如果它像链接列表一样,插入将是O(1),而如果它像数组一样实现,它将是线性的,如你所说。

答案 6 :(得分:0)

取决于您需要容器支持哪些操作。如果你可能需要在任何给定的时间删除min元素,min-heap是最好的,尽管有几个操作是非常重要的(在某些情况下是分摊的log(n)时间)。

但是,如果您只需要从前/后推/弹,您可以使用一个mindeque,它可以为所有操作(包括findmin)实现分摊的常量时间。您可以a scholar.google.com search了解有关此结构的更多信息。我和我的一位朋友最近合作,以便更容易理解并实现一个mindeque版本。如果您正在寻找这个,我可以为您发布详细信息。