Looking into another question I bumped into this intriguing behavior of the 1.8.0_112 Sun-Oracle compiler (I have not tested with others):
import java.util.List;
interface Alpha<T> {
List<Integer> intList();
}
interface Beta {
List<Integer> intList();
}
class Main {
public static void main(String[] args) {
Alpha rawAlpha = null;
Alpha<Character> charAlpha = null;
Alpha<?> qmAlpha = null;
Beta beta = null;
for (Integer i : charAlpha.intList()) {}
for (Integer i : qmAlpha.intList()) {}
for (Integer i : beta.intList()) {}
for (Integer i : rawAlpha.intList()) {}
}
}
The compiler only fails at the last for loop:
error: incompatible types: Object cannot be converted to Integer
for (Integer i : rawAlpha.intList()) {}
^
1 error
So despite that intList()
return list type List<Integer>
in Alpha
does not depend on the type parameter T
, it seems that the <Integer>
is erased at compilation time.
Notice that if we declare a non-generic interface Beta
that would be, in theory, equivalent to making reference to the raw Alpha
, there is no issues.
Is this the expected behavior? can some one point out the paragraph on the language spec that would cover this point? If this is not a bug at the very least it seem rather anti-intuitive and non-productive; perhaps is done for the sake of back-comparability?.