Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Odd generics behaviour of List.toArray(T[])

Tags:

I came across something very basic but extremely bewildering today. I needed to convert a list to an array. The list contained String instances. Perfect example of using List.toArray(T[]), since I wanted a String[] instance. It would not work, however, without explicitly casting the result to String[].

As a test scenario, I used the following code:

import java.util.Arrays; import java.util.List;  public class MainClass {     public static void main(String args[]) {         List l = Arrays.asList("a", "b", "c");         String stuff[] = l.toArray(new String[0]);         System.err.println(Arrays.asList(stuff));     } } 

which does not compile. It's nearly an exact copy of the example in the javadoc, yet the compiler says the following:

MainClass.java:7: incompatible types found   : java.lang.Object[] required: java.lang.String[]     String stuff[] = l.toArray(new String[0]);                           ^ 

If I add a cast to String[] it will compile AND run perfectly. But that is not what I expect when I looked at the signature of the toArray method:

<T> T[] toArray(T[] a) 

This tells me that I shouldn't have to cast. What is going on?

Edit:

Curiously, if I change the list declaration to:

List<?> l = Arrays.asList("a", "b", "c"); 

it also works. Or List<Object>. So it doesn't have to be a List<String> as was suggested. I am beginning to think that using the raw List type also changes how generic methods inside that class work.

Second edit:

I think I get it now. What Tom Hawtin wrote in a comment below seems to be the best explanation. If you use a generic type in the raw way, all generics information from that instance will be erased by the compiler.

like image 704
waxwing Avatar asked Jul 02 '09 11:07

waxwing


1 Answers

you forgot to specify the type parameter for your List:

List<String> l = Arrays.asList("a", "b", "c"); 

in this case you can write safety:

String[] a = l.toArray(new String[0]); 

without any cast.

like image 166
dfa Avatar answered Jan 03 '23 11:01

dfa