Подтвердить что ты не робот

Обобщение и сортировка в Java

Предположим, вы пишете статическую функцию в Java для сортировки массива, подобно Arrays.sort(). Проблема с Arrays.sort() заключается в том, что он получает массив объекта и выбрасывает ClassCastException, если его элементы не реализуют Comparable.

Итак, вы хотите, чтобы ваша функция получала в качестве аргумента массив подтипа Comparable. Что-то вроде этого может работать:

static <T extends Comparable> void sort(T[] array);

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

Итак, как вы можете создать функцию, которая получит только массив, элементы которого реализуют Comparable и имеют одинаковый тип (например, Integer, String и т.д.?)

4b9b3361

Ответ 1

Используйте

static <T extends Comparable<? super T>> sort(T[] array);

который является самой общей спецификацией для выполнения задачи. В принципе, он утверждает, что T - это тип, который можно сравнить с самим собой.

Ответ 2

Ответ Dirk - это лучшее, что вы можете получить, но Google Collections использовались точно так же, как вы писали, чтобы избежать ошибки в javac:

Почему вы используете тип <E extends Comparable> в различных API-интерфейсах, который не "полностью размножается"? Не должно быть <E extends Comparable<?>>, <E extends Comparable<E>> или <E extends Comparable<? super E>>?

Последнее предложение является правильным, как объяснено в "Эффективном" Ява. Однако мы будем использовать <E extends Comparable<E>> on без параметров, чтобы обойти ужасную ошибку javac. Это вызовет проблемы при использовании очень необычного типа, например java.sql.Timestamp, что сопоставимо с супертипом.     (Требуется больше объяснений.)

От: http://code.google.com/p/google-collections/wiki/Faq

Теперь это вам...

Ответ 3

В мире post-1.5 Java справочные массивы представляют собой только детали реализации на низком уровне. Предпочитаете, коллекции.

Если вас интересуют справочные массивы, по какой-то своеобразной причине, вы будете знать, что они действительно не получают дженериков. Вы не можете (разумно) иметь массив общего типа, например Comparable<String>. Это означает, что если Arrays.sort было обобщено аналогично Collections.sort, оно было бы более ограниченным.

Из-за особенностей типизации массива, если вы действительно хотите перенапрягать типы, я думаю, что sort можно написать проще, чем Collections.sort, не жертвуя чем-то значительным.

public static <T extends Comparable<T>> sort(T[] array)

Если вы хотите иметь двоичную совместимость с предварительными генериками, вам понадобится небольшой взлом, чтобы вернуться к подписи Object[], аналогично Collections.min.

public static <T extends Object & Comparable<T>> sort(T[] array)