question about applicability inference with wildcards and deferred types

Liam Miller-Cushon cushon at google.com
Tue May 6 18:18:06 UTC 2014


I encountered an example where javac8 can't perform applicability inference
for a method in the presence of wildcards. This only occurs with -source 8
-target 8. I think it is related to JDK-7177387, since the behaviour goes
away when Source.allowPoly() is disabled.


Here's the code:


===

import java.util.List;


abstract class Test {

  abstract <T> List<T> copyOf(List<? extends T> lx);

  abstract <E> List<E> filter(List<E> lx);


  // This works:

  <U> void f(List<U> lx) {

    copyOf(filter(lx));

  }


  // This doesn't:

  void g(List<?> lx) {

    copyOf(filter(lx));

  }

}

===


The interesting bit of the error message is:


error: method copyOf in class Test cannot be applied to given types;

...

List<CAP#2> cannot be converted to List<? extends CAP#2>


I think that the logic in Types.containsType could be improved to handle
this case better. Turning on the debug output (Types.debugContainsType)
reveals that javac is checking:


does "? extends capture#630 of ?" contain "capture#630 of ?" ?

=> U(capture#630 of ?) <: U(? extends capture#630 of ?)

=> java.lang.Object <: capture#630 of ?

=> false


My theory is that prior to javac8 the inferencer did not encounter
wildcards whose bound was a captured wildcard (? extends CAP of ?), and
that changed with the addition of deferred types in JDK-7177387. Perhaps
some additional logic could be added to containsType(T, S) to deal with S
being the upper bound of T?


Thanks,

Liam
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.openjdk.java.net/pipermail/compiler-dev/attachments/20140506/8e3f6552/attachment.html>


More information about the compiler-dev mailing list