FULL PRODUCT VERSION : java version "1.8.0_60" Java(TM) SE Runtime Environment (build 1.8.0_60-b27) Java HotSpot(TM) 64-Bit Server VM (build 25.60-b23, mixed mode) ADDITIONAL OS VERSION INFORMATION : Microsoft Windows [Version 10.0.10240] A DESCRIPTION OF THE PROBLEM : Consider an overloaded method that takes two different functional interfaces as parameters (`Runnble` and `Supplier`). `System.out.println` is clearly only compatible with `Runnable`, because it is a `void` method. javac agrees, reporting an error that explicitly notes that the return type of `Supplier` cannot be converted to void. Yet javac still claims in a separate error that the call is ambiguous and matches both `Runnable` and `Supplier`. Note that both lambda `() -> {}` and method reference `System.out::flush` are able to resolve. The difference appears to be that `System.out.println` is overloaded with versions that take an argument. As none of those overloaded versions match either `Supplier` or `Runnable`, it is unclear how they would be relevant here. Another note is that this does resolve correctly and compile with the Eclipse compiler. STEPS TO FOLLOW TO REPRODUCE THE PROBLEM : >javac.exe -cp . GenericLambdas.java EXPECTED VERSUS ACTUAL BEHAVIOR : EXPECTED - Ability to successfully compile and run. javac should select this overloaded version of wrap: static void wrap(Runnable function){} ACTUAL - javac is unable to compile the class ERROR MESSAGES/STACK TRACES THAT OCCUR : GenericLambdas.java:5: error: reference to wrap is ambiguous wrap(System.out::println); ^ both method <R>wrap(Supplier<R>) in GenericLambdas and method wrap(Runnable) in GenericLambdas match where R is a type-variable: R extends Object declared in method <R>wrap(Supplier<R>) GenericLambdas.java:5: error: incompatible types: cannot infer type-variable(s) R wrap(System.out::println); ^ (argument mismatch; bad return type in method reference void cannot be converted to R) where R is a type-variable: R extends Object declared in method <R>wrap(Supplier<R>) 2 errors REPRODUCIBILITY : This bug can be reproduced always. ---------- BEGIN SOURCE ---------- import java.util.function.Supplier; public class GenericLambdas { public static void main(String[] args) { wrap(System.out::println); // Compiler error here wrap(() -> {}); // No error } static <R> void wrap(Supplier<R> function) {} static void wrap(Runnable function) {} } ---------- END SOURCE ---------- CUSTOMER SUBMITTED WORKAROUND : Explicitly casting the method reference to `Runnable`: wrap((Runnable) System.out::println);
|