Gen iOb; Внимательно проанализируем это объявление. В первую очередь обратите внимание на то, что тип Integer указывается в угловых скобках после имени класса Gen. В данном случае Integer служит аргументом типа, передаваемым в качестве параметра типа Т класса Gen. В рассматриваемом здесь объявлении создается версия класса Gen, в которой тип Т заменяется типом Integer везде, где он встречается. Следовательно, после этого объявления Integer становится типом переменной ob и возвращаемым типом метода getob . Прежде чем продолжить рассмотрение обобщений, следует принять во внимание то обстоятельство, что компилятор Java на самом деле не создает разные версии Gen или другого обобщенного класса, а просто удаляет данные обобщенного типа, заменяя их приведением типов. Получаемый в итоге объект ведет себя так, как будто в программе была создана конкретная версия класса Gen. Таким образом, в программе фактически присутствует лишь одна версия класса Gen. Процесс удаления данных обобщенного типа называется стиранием, более подробно рассматриваемым в конце этой главы. В следующей строке кода переменной iOb присваивается ссылка на экземпляр в версии класса Gen для типа Integer:
iOb = new Gen(88);
Обратите внимание на то, что при вызове конструктора класса Gen указывается также аргумент типа Integer. Это необходимо потому, что тип объекта, на который указывает ссылка (в данном случае — iOb), должен соответствовать Gen
iOb = new Gen(88.0); // Ошибка!
Переменная iOb относится к типу Gen
iOb = new Gen(88);
производится автоупаковка целочисленного значения 88 в объект типа Integer. Это происходит потому, что обобщение Gen
iOb = new Gen(new Integer(88)); Но в данном случае столь длинная строка кода не дает никаких преимуществ по сравнению с предыдущей, более компактной записью. Затем в программе отображается тип переменной ob в объекте iOb (в данном случае это тип Integer). А значение переменной ob получается в следующей строке кода:
int v = iOb.getobO;
Метод getob возвращает значение типа Т, замененное на Integer при объявлении переменной ссылки на объект iOb, а следовательно, метод getob фактически возвращает значение того же самого типа Integer. Это значение автоматически распаковывается перед присваиванием переменной v типа int.
И наконец, в классе GenDemo объявляется объект типа Gen
Gen strOb = new Gen("Generics Test"); В этом объявлении указывается аргумент типа String, поэтому в объекте класса Gen вместо Т подставляется тип String. В итоге создается версия класса Gen для типаString, как демонстрируют остальные строки кода рассматриваемой здесь программы. ### Действие обобщений распространяется только на объекты При определении экземпляра обобщенного класса аргумент типа, передаваемый в качестве параметра типа, должен обозначать тип класса. Для этой цели нельзя использовать простой тип, например int или char. В примере с классом Gen в качестве параметра типа Т можно передать любой класс, но не простой тип данных. Иными словами, следующее объявление недопустимо: