Why compiler do not produce any error? Where in JLS I can read about this situation?
class Main {
public static void main(String[] args) {
A a = new A();
List<Integer> list = a.getStrings();
}
static class A<X> {
public List<String> getStrings() {
return new ArrayList<String>();
}
}
}
You can read about this situation in JLS §4.8:
The use of raw types is allowed only as a concession to compatibility of legacy code. The use of raw types in code written after the introduction of generics into the Java programming language is strongly discouraged. It is possible that future versions of the Java programming language will disallow the use of raw types.
To make sure that potential violations of the typing rules are always flagged, some accesses to members of a raw type will result in compile-time unchecked warnings. The rules for compile-time unchecked warnings when accessing members or constructors of raw types are as follows:
At an assignment to a field: if the type of the left-hand operand is a raw type, then a compile-time unchecked warning occurs if erasure changes the field's type.
At an invocation of a method or constructor: if the type of the class or interface to search (§15.12.1) is a raw type, then a compile-time unchecked warning occurs if erasure changes any of the formal parameter types of the method or constructor.
No compile-time unchecked warning occurs for a method call when the formal parameter types do not change under erasure (even if the result type and/or throws clause changes), for reading from a field, or for a class instance creation of a raw type.
This is what's called using a raw type. This is in the language for legacy reasons because generics was not always a part of Java.
And since you don't use the generic type parameter anyway it just gets erased. As the commenter pointed out If you don't specify a type parameter after type erasure it will be an Object.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With