【问题标题】:Finding second maximum in an array in most efficient way以最有效的方式在数组中查找第二个最大值
【发布时间】:2013-09-28 08:36:34
【问题描述】:

我试图在空间和时间复杂度方面以最有效的方式找到数组中的第二个最大值,但我有两个主要问题:

1. 时间复杂度:

天真的或蛮力方法需要两次才能找到最小的元素,因此复杂度为 O(n),如果我对数组进行排序,则需要 O(n2)。

2. 空间复杂度:

我总是可以使用 BST 进行 O(log(n)) 排序,但它们需要额外的空间来维护树,我还可以创建一个堆并执行两次删除,我会得到第二大元素,但这里也是堆被创建并存储在内存中。

我有什么选择?

【问题讨论】:

标签: algorithm sorting


【解决方案1】:

您可以一次性完成此操作。只需保留两个变量,最大值和第二个最大值。 每次更新最大值时,旧的最大值都会变成新的第二个最大值。

这推广到 Top-k 算法,您可以使用一次遍历和 O(k) 空间找到k 最大(或最小)的元素。在你的情况下k=2

【讨论】:

  • 好的,我知道了,谢谢。但是我可以在登录时进一步改进它吗?
  • @Charlie - 正如您在问题中指出的那样,只有先排序,这会产生额外的开销。通常,仅当您将按特定顺序多次搜索/访问列表时才需要排序。
  • 时间或空间登录?这是 k=2 的 O(1) 空间。
  • 如果你排序,那么这将变成 O(1) 时间。只需查看倒数第二个元素。
  • 排序需要 O(nlogn) 的时间。
【解决方案2】:

在列表中找到第 n 个最大的项目称为选择问题,有很多算法可以解决它。 http://en.wikipedia.org/wiki/Selection_algorithm

您可以实现的 lis 最低复杂度是 O(n),因为您需要至少查看列表中的每个项目一次。例如,使用部分插入排序(遍历列表并跟踪前 k 个元素)可以在 O(kn) 时间内从 n 个列表中找到前 k 个项目。

有一种称为 quickselect 的算法可以在 O(n) 时间内找到前 k 个项目,与 k 无关。我建议查找它,但要找到前 2 个,扫描列表一次的简单方法就足够了。

【讨论】:

  • 感谢您提到快速选择。它已成为Rosetta Code 上的一项任务,其中已经有 Python、Perl 6 和 Tcl 中的算法示例。
猜你喜欢
  • 2015-05-22
  • 1970-01-01
  • 2015-04-06
  • 1970-01-01
  • 2019-08-05
  • 2011-01-24
  • 1970-01-01
  • 2017-04-03
  • 2018-04-07
相关资源
最近更新 更多