Какую коллекцию Java следует использовать для хранения уникальных элементов в отсортированном порядке?

«Какую коллекцию Java следует использовать для хранения уникальных элементов в отсортированном порядке?» — вопрос из категории Алгоритмы и структуры данных, который задают на 10% собеседований Java Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Для хранения уникальных элементов с автоматической сортировкой следует использовать TreeSet<E>.

Почему TreeSet?

  • Реализует интерфейс SortedSet и NavigableSet.
  • Гарантирует уникальность элементов (как и все Set).
  • Автоматически поддерживает порядок сортировки при каждой вставке или удалении.

Способ сортировки:

  1. Естественный порядок (Natural Ordering): Элементы должны реализовывать интерфейс Comparable.
  2. Через Comparator: В конструктор можно передать объект Comparator для кастомной логики сортировки.

Пример использования:

// 1. Сортировка по натуральному порядку (для Integer, String и т.д.)
SortedSet<Integer> numbers = new TreeSet<>();
numbers.add(10);
numbers.add(5);
numbers.add(10); // Дубликат не добавится
numbers.add(2);
System.out.println(numbers); // Вывод: [2, 5, 10]

// 2. Сортировка с помощью Comparator (например, по убыванию)
SortedSet<Integer> descendingNumbers = new TreeSet<>(Comparator.reverseOrder());
descendingNumbers.addAll(numbers);
System.out.println(descendingNumbers); // Вывод: [10, 5, 2]

Характеристики и предостережения:

  • Сложность операций: add(), remove(), contains() работают за O(log n), так как TreeSet реализован на основе красно-черного дерева.
  • null значения: Не допускаются при использовании натурального порядка. Могут быть разрешены только если переданный Comparator явно обрабатывает null.
  • Потокобезопасность: Не синхронизирован. Для использования в многопоточных сценариях требуется внешняя синхронизация: SortedSet s = Collections.synchronizedSortedSet(new TreeSet(...));

Альтернатива: Если нужен порядок вставки, а не сортировки, но с уникальностью — используйте LinkedHashSet.