Search code examples
javagenericsraw-types

Printing String from a Integer list's index


I am running this small piece of code:

List<String> abc = new ArrayList<String>();
abc.add("something");
List raw = abc;
List<Integer> def = raw;
System.out.println(def.get(0));

I don't understand why it is not throwing an exception when the list containing a String member is being assigned to an Integer List. Moreover, how is an Integer list storing and printing a String? Can someone help me out here?


Solution

  • This is the reason why you shouldn't use raw types.

    When you do

    List raw = abc;
    

    You, yourself erasing the type with list. So They are free of types and no error from compiler. To gain the benefits of generics you should avoid using raw types.

    And also consider reading about Type Erasing. At run time the lists do not have any idea about their types. Types get erased and they just get whatever available in the list.

    The error you expected is a compiler error and at the same time you avoided giving a type first. Hence there is no error.

    If you really want to see an exception, try to assign an element from the current list to an Integer. Though compiler won't give you any error, at runtime the types get match and you run into exception.

    If you have a look at Raw Types docs, you see almost same example

    Box<String> stringBox = new Box<>();
    Box rawBox = stringBox;
    rawBox.set(8);  // warning: unchecked invocation to set(T)
    

    The warning shows that raw types bypass generic type checks, deferring the catch of unsafe code to runtime. Therefore, you should avoid using raw types.