O (log n) алгоритм поиска max массива?

существует ли алгоритм, который находит максимум несортированного массива за время O(log n)?

8 ответов


этот вопрос задается много (это популярный вопрос домашней работы CS или что-то еще?) и ответ всегда один: нет.

об этом думать математически. Если массив не отсортирован, нет ничего, чтобы "разрезать пополам", чтобы дать вам log(n) поведение.

прочитайте комментарии к вопросу для более глубокого обсуждения (что, вероятно, выходит за рамки вопроса).


рассмотрим это: без посещения каждый элемент, откуда вы знаете, что какой-то элемент, который вы не посетили, не больше, чем самый большой, который вы нашли до сих пор?


это невозможно сделать в O(log(N)). Это O(N) в лучшем/худшем / среднем случае, потому что нужно было бы посетить каждый элемент в массиве, чтобы определить, является ли он larges one или нет. Массив несортирован, что означает, что вы не можете вырезать углы.

даже в случае parallelisation, это не может быть сделано в O(N), потому что Big-O нотация не заботится о том, сколько CPU у одного есть или какова частота каждого процессора. Оно абстрагировано от этого специфически чтобы дать сырой estamate проблемы.

распараллеливанием можно пренебречь, поскольку время, затраченное на разделение задания, можно считать равным времени последовательного выполнения. Это связано с тем, что константы игнорируются. Все это одно и то же:

O(N) = O(Const * N) = O(N / Const) = O(N + Const) = O(N - Const)

С другой стороны, на практике "разделяй и властвуй" параллельные алгоритмы можем дать вам некоторые преимущества в производительности, поэтому он может работать немного быстрее. К счастью, Big-O не работает с помощью этого мелкозернистого алгоритмического анализа сложности.


нет. Это O (n). В худшем случае все члены массива должны быть посещены и сравнены.


нет. вы должны пройти через массив хотя бы один раз.


конечно, нет . предположим, что все еще есть элемент, который вы еще не сравнили с любым другим элементом . таким образом, нет никакой гарантии, что элемент, который вы не сравнивали, не является максимальным элементом

и предположим, что ваш сравнивающий граф (вершины для элементов и ребра для сравнения ) имеет более одного компонента . в этом случае вы должны поставить ребро (наилучшим образом между максимум двумя компонентами).мы видим, что при N-1 операция должна быть выполнена


это очень старый, но я не согласен с ответами. да, это можно сделать, с параллельным оборудованием, в логарифмическом времени.

сложность будет такой:

O(log(n) * log(m))

n - это количество чисел, сравнивать; m - размер каждого номера.

однако размер оборудования будет:

O(n * m)

алгоритм такой:

  1. сравнение чисел в парах. Время is O(log(m)), и размер составляет O(n * m), используя снесите вперед компараторы.

  2. используйте результат в 1 для мультиплексирования обоих входов 1. Время это O(1), и размер составляет O(n * m).

  3. теперь у вас есть массив вдвое меньше начального размера; перейдите к шагу 1. Этот цикл повторяется log(n) раз, так что общее время составляет O(log(n) * log(m)), а общий размер -O(n * m).

добавление еще нескольких Муксов вы также можете отслеживать индекс наибольшее число, если оно вам нужно, без увеличения сложности алгоритма.


если вы используете , Это можно сделать в O(log N) времени. Но ... --6-->Работы Сложности по-прежнему O(N).

при использовании , вы можете уменьшить сложность времени O(1) С применением алгоритм Усэйна Болта.