是否存在在O(log n)时间内找到未排序数组的最大值的算法?
答案 0 :(得分:17)
这个问题被问了很多(这是一个受欢迎的CS家庭作业问题吗?),答案总是一样的:没有。
以数学方式思考。除非对数组进行排序,否则没有什么可以“减半”来为您提供log(n)
行为。
阅读问题评论以进行更深入的讨论(无论如何,这可能超出了问题的范围)。
答案 1 :(得分:8)
考虑一下:如果不访问每个元素,你怎么知道你没有访问过的某个元素不比你到目前为止找到的最大元素大?
答案 2 :(得分:5)
O(log(N))
无法做到这一点。在最佳/最差/平均情况下,O(N)
是因为需要访问数组中的每个项目以确定它是否是大数据。数组未排序,这意味着你不能偷工减料。
即使在并行化的情况下,这也不能在O(N)
中完成,因为 Big-O 表示法并不关心每个CPU有多少或每个CPU的频率是多少中央处理器。它是专门从这个问题中抽象出来的,以便给出问题的原始内容。
可以忽略并行化,因为划分作业所花费的时间可以被认为等于顺序执行的时间。这是由于常数被忽视的原因。以下是完全相同的:
O(N) = O(Const * N) = O(N / Const) = O(N + Const) = O(N - Const)
另一方面,在实践中,分而治之的并行算法可以为您带来一些性能优势,因此可以更快地运行。幸运的是, Big-O 并不处理这种细粒度的算法复杂性分析。
答案 3 :(得分:4)
没有。这是O(n)。在最坏的情况下,必须访问和比较阵列的所有成员。
答案 4 :(得分:1)
当然不是。假设还有一个元素,你还没有将它与任何其他元素进行比较。所以不能保证你没有比较的元素不是最大元素
并假设您的比较图(元素和边的顶点用于比较)具有多个组件。在这种情况下,你必须设置一个边缘(最好的方式是在最多两个组件之间)。我们可以看到在n-1操作必须完成
答案 5 :(得分:0)
这是非常古老的,但我不同意给出的答案。 是,可以使用并行硬件在对数时间内完成。
时间复杂度将是:
O(log(n) * log(m))
n
是要比较的数字数量; m
是每个数字的大小。
但是,硬件大小为:
O(n * m)
算法将是:
成对比较数字。使用进位超前比较器,时间为O(log(m))
,大小为O(n * m)
。
使用1中的结果复用两个输入1.时间为O(1)
,大小为O(n * m)
。
现在你有一个初始大小的一半的数组;转到第1步。此循环重复log(n)
次,因此总时间为O(log(n) * log(m))
,总大小为O(n * m)
。
如果需要,您还可以添加更多MUX,也可以跟踪最大数量的索引,而不会增加算法的复杂性。
答案 6 :(得分:0)
我认为使用细分树可能会有所帮助,您可以实现log(N)成本。
答案 7 :(得分:-1)
如果使用N
处理器,则可以在O(log N)
时间内完成。
但是工作复杂度仍然是O(N)
。
如果使用N^2
处理器,则可以通过应用 Usain Bolt算法将时间复杂度降低到O(1)
。