Когда следует использовать TreeMap над PriorityQueue и наоборот?

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

Ответ 1

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

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

Ответ 2

Полностью согласен с Эриксоном в том, что очередь с приоритетами дает только минимальный/максимальный элемент.

Кроме того, поскольку очередь приоритетов менее мощна для поддержания общего порядка данных, она имеет преимущество в некоторых особых случаях. Если вы хотите отслеживать самые большие M элементов в массиве из N, сложность по времени будет O(N*LogM) а сложность пространства будет O(M). Но если вы делаете это на карте, временная сложность составляет O(N*logN) а пространство - O(N). Это довольно фундаментально, в то время как в некоторых случаях мы должны использовать приоритетную очередь, например, M это просто константа, такая как 10.

Ответ 3

Есть два отличия, которые я хотел бы указать (и это может быть более актуальным для Разница между PriorityQueue и TreeSet в Java?, поскольку этот вопрос считается дублированным этого вопроса).

(1) PriorityQueue может иметь дубликаты, где TreeSet не может иметь дубликатов. Поэтому в Treeset, если ваш компаратор считает 2 элемента равными, TreeSet будет удерживать только один из этих двух элементов и выбросить другой.

(2) Итератор TreeSet перемещает коллекцию в отсортированном порядке, тогда как Итератор PriorityQueue НЕ перемещается в отсортированном порядке. Для PriorityQueue Если вы хотите получить элементы в отсортированном порядке, вам нужно уничтожить очередь, вызвав remove() несколько раз.

Я предполагаю, что обсуждение ограничено реализацией Java этих структур данных.

Ответ 4

Правило большого пальца об этом:

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

PriorityQueue гарантирует только мин или макс. Это дешевле, но менее мощно.

Ответ 5

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

  • PriorityQueue Позволяет дублировать (с тем же приоритетом), пока TreeMap не делает.
  • Сложность PriorityQueue - O (n) (когда увеличивается ее размер), а для TreeMap - O (logn) (поскольку она основана на Red Black Tree)
  • PriorityQueue основан на массиве, в то время как узлы TreeMap связаны друг с другом, поэтому метод PriorityQueue будет принимать O (n) время, а TreeMap будет принимать время O (logn).

Ответ 6

Одно из отличий заключается в том, что remove (Object) и содержит (Object) являются линейными O (N) в обычной PriorityQueue (например, Oracle), но O (log (N)) для TreeSet/Map.

Итак, если у вас есть большое количество элементов и много удаляет (Object) или содержит (Object), то TreeSet/Map может быть быстрее.

Ответ 7

Это зависит от того, как вы реализуете приоритет очереди. Согласно книге Кормена 2-й из них, самый быстрый результат - с кучей Фибоначчи.