2013-09-05 3 views
1

У меня есть заводской метод дженериков.Как узнать JVM тип генераторов без аргументов?

public static <T> List<T> create(){ 
    return new ArrayList<T>(); 
} 

Но у него нет аргументов/параметров.

Я не даю параметр типа для функции, но он знает соответствующий тип без каких-либо аргументов.

public static void main(String[] args){ 
    List<Integer> intlist = create(); //it is an Integer List 
    List<String> stringlist = create(); //it is a String List 
} 
+3

Это делается с левой стороны декларации. –

+0

Это, вероятно, один из немногих не совсем бесполезных случаев, когда общий параметр, используемый только один раз в сигнатуре метода, имеет смысл. (Хотя и не так много с оператором алмаза, присутствующим в Java 7.) – millimoose

ответ

6

JVM не знает параметр типового типа из-за стирания типа.

Java-компилятор может сделать вывод, что T должен быть Integer или String в ваших примерах, потому что он имеет доступ к информации типа родовой о типах переменных вы объявлены.

+0

Итак, для JVM это «List intlist = new ArrayList;» в обоих случаях (Integer, String) из-за стирания типа? – user2693979

+0

@ user2693979 Это правильно. – rgettman

+2

@ user2693979 Для JVM это просто 'List' и' ArrayList', последний из которых содержит 'Object []'. Тип erasure означает, что общая информация типа неявно привязана к * экземплярам *. (Вы все равно можете присоединить его явно, передав объекты класса «Class», и информация сохраняется в объявлениях типов и методов, доступных для отражения.) – millimoose

1

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

Другая точка зрения заключается в том, что, когда общий параметр явно не задан, компилятор не имеет значения, что именно такой параметр. В конце концов, параметр типа не влияет на скомпилированный байт-код вообще. Он просто должен быть в состоянии доказать, что существует некоторый параметр типа, который заставил бы его работать; и это все равно. Для ситуации может быть несколько допустимых параметров типа; но неважно, какой из них «используется», потому что он не влияет на результат. В этом случае, поскольку метод не принимает аргументов и возвращает List<T>, где T является общим для этого метода, если он используется в контексте, который принимает List, он действителен, поскольку независимо от List<what exactly>, действительный T есть (T = whatever type parameter is desired). Поэтому в этом случае компилятору вообще не нужно проверять параметр типа.

Смежные вопросы