Incoherent invocation type inference?
B. Blaser
bsrbnd at gmail.com
Fri Jan 13 13:01:26 UTC 2017
Hi,
I encountered a strange behavior in the the case of a poly expression
method invocation (with 'null' or without parameter) that doesn't
provide any explicit type argument (JLS 18.5.2).
The following code:
import java.util.*;
public class Issue {
<T extends Iterable<String>> T get() { return (T)new ArrayList<String>(); }
<T extends Iterable<String>> T get(T t) { return (T)new
ArrayList<String>(); }
void run() {
List<String> li = null;
LinkedList<String> ll = null;
Integer i = null;
li = get(null);
i = get(null); // Shouldn't compile? and will fail at runtime.
// i = get(li); // Fails as expected
li = get();
ll = get(); // OK, but will fail at runtime due to unchecked
conversion in get().
i = get(); // Shouldn't compile? and will fail at runtime.
}
public static void main(String... args) {
new Issue().run();
}
}
...is translated as follows before code generation:
public class Issue {
public Issue() {
super();
}
Iterable get() {
return (Iterable)new ArrayList();
}
Iterable get(Iterable t) {
return (Iterable)new ArrayList();
}
void run() {
List li = null;
LinkedList ll = null;
Integer i = null;
li = (List)get(null);
i = (Integer)get(null);
li = (List)get();
ll = (LinkedList)get();
i = (Integer)get();
}
public static void main(String... args) {
new Issue().run();
}
}
The next line is OK, but will fail at runtime due to unchecked
converstion in get():
ll = (LinkedList)get();
But the following lines are more surprising:
i = (Integer)get(null);
i = (Integer)get();
They will, of course, fail at runtime with ClassCastException. I think
that javac behavior is probably in compliance with JLS 18.5.2, but is
this really coherent?
Thanks,
Bernard
More information about the compiler-dev
mailing list