Por que List .toArray () retorna Object e não String ? como contornar isso?

Alguém sabe por que o Java 1.6 tem esse comportamento:

List list = ArrayList(); String[] arr = (String[]) list.toArray(); 

E eu recebo um ClassCastException, porque retorna Object [] e não String [].

Eu pensei que List.toArray() deveria retornar T [] – não? Alguém tem uma resposta porque esse inconveniente existe no idioma? E também como contornar isso? Como eu obtenho um String [] de List sem loop através dos itens?

Você precisa passar em uma matriz para que seu tipo de tempo de execução possa ser usado como uma dica por toArray . Tente toArray(new String[0]) vez disso. Você também pode passar uma matriz pré-dimensionada.

Para entender, considere que tipo de apagamento teria que fazer para

 new T[4] 

trabalhos. Se Java permitiu isso, o melhor que poderia fazer pós-apagamento é

 new Object[4] 

A maioria toArray implementações do toArray usa java.lang.reflect.Array para construir uma matriz de saída do tipo certo, dada uma dica de tipo passada como uma Class .

Como os arrays estão em Java desde o início, enquanto os genéricos foram introduzidos apenas no Java 5. E o método List.toArray() foi introduzido no Java 1.2, antes dos genéricos existirem, e por isso foi especificado para retornar Object[] . Muitos códigos existentes agora esperam que List.toArray() retorne Object[] , portanto, não pode ser alterado agora.

Além disso, os genéricos são apagados em tempo de execução, de modo que o ArrayList não poderia sequer construir um array do tipo apropriado se quisesse.

A lacuna para isso é o List.toArray(T[]) , que retornará uma matriz do tipo correto, desde que você atribua a ela uma matriz do tipo correto para que saiba qual tipo usar.

Para entender por que isso acontece, basta dar uma olhada no javadoc para Collection.toArray() e então olhar para o método Collection.toArray(T[] a) . Também tenha em mente que os genéricos em Java são apagados em tempo de execução.

As razões são duas:

  1. O método precedeu o Generics e eles não puderam alterar a assinatura sem quebrar a compatibilidade.

  2. Em qualquer caso, como a List é construída sem uma Class não há como a implementação construir uma matriz do tipo T

A solução alternativa será usar:

  List list = new ArrayList<>(); list.add("Sputnik"); list.add("Explorer"); //String[] str = list.toArray(); 

Isto é obrigado a lançar um: tipos incompatíveis: Object [] não pode ser convertido para erro String []

  Instead use: String[] str = list.toArray(new String[0]); or String[] str = list.toArray(new String[list.size()]);