Q:

Generic и массивы

Доброго всем времени!
Думал, что я знаю, как использовать дженерики, а оказалось xто и нет. Код:
class MyClass<T> {
   T mas[];

   void foo() {
       mas = new T[10]; // ошибка!
   }
}

Вопрос - почему возникает ошибка?

A:

Это ограничение реализации дженериков в Java.
Дело в том, что дженерики — конструкция времени компиляции, информации о настоящем типе в рантайме нет. Это называется type erasure: Java заменяет везде T на Object в скомпилированном коде (если нет дальнейших условий). При создании массива, однако, Java нуждается в информации о типе элементов, но этот тип недоступен, дженерик не имеет возможности узнать тип своего параметра T!
Поэтому и создать массив неизвестного (для дженерика) типа T в Java невозможно.

В качестве рекламы корпорации мирового зла замечу, что дженерики в C# были разработаны с учётом опыта Java и избежали проблемы, с которой вы столкнулись.

На Stackoverflow обсуждаются возможные workaround'ы. Самый простой — передавать T.class в конструкторе MyClass<T>, и конструировать массив следующим образом:
mas = (T[])Array.newInstance(TClass, 10);

A:

@nightin_gale, Еще один вариант так сказать "из жизни": вместо поля TClass объявить абстрактный метод в духе:
protected Class<T> getClassDef();

и, переопределяя его в дочерних классах:
public class MyStringClass extends MyClass<String> {   
  protected Class<T> getClassDef() { return String.class; }
}

пользоваться в родительском:
mas = (T[])java.lang.reflect.Array.newInstance(getClassDef(), 10);

