Я также не уверен, почему есть ограничение. Вы можете попробовать отправить дружеское электронное письмо разработчикам Java 5 Generics (главным образом, Гиладу Браче и Нилу Гафтеру).
Я предполагаю, что они хотели поддерживать только абсолютный минимум типов пересечений (то есть, по сути, множественные границы), чтобы сделать язык не более сложным, чем необходимо. Пересечение не может использоваться как аннотация типа; программист может выражать пересечение только тогда, когда оно отображается как верхняя граница переменной типа.
И почему этот случай даже был поддержан? Ответ заключается в том, что множественные границы позволяют управлять стиранием, что позволяет поддерживать двоичную совместимость при обобщении существующих классов. Как объясняется в разделе 17.4 книги Нафталина и Вадлера, метод max
логически будет иметь следующую подпись:
public static <T extends Comparable<? super T>> T max(Collection<? extends T> coll)
Однако, это стирает до:
public static Comparable max(Collection coll)
Который не соответствует исторической подписи max
и приводит к поломке старых клиентов.
При множественных границах для стирания рассматривается только крайняя левая граница, поэтому если max
задана следующая подпись:
public static <T extends Object & Comparable<? super T>> T max(Collection<? extends T> coll)
Тогда стирание его подписи становится:
public static Object max(Collection coll)
Что равно сигнатуре max
перед Generics.
Кажется правдоподобным, что разработчики Java заботились только об этом простом случае и ограничивали другое (более продвинутое) использование типов пересечений, потому что они просто не знали, какую сложность это может принести. Таким образом, причиной такого конструктивного решения не должна быть возможная проблема безопасности (как предполагает вопрос).
Дальнейшее обсуждение типов пересечений и ограничений дженериков в следующей статье OOPSLA .