質問に答えていて、説明できないシナリオに出くわしました。このコードを考えてみましょう:
interface ConsumerOne<T> {
void accept(T a);
}
interface CustomIterable<T> extends Iterable<T> {
void forEach(ConsumerOne<? super T> c); //overload
}
class A {
private static CustomIterable<A> iterable;
private static List<A> aList;
public static void main(String[] args) {
iterable.forEach(a -> aList.add(a)); //ambiguous
iterable.forEach(aList::add); //ambiguous
iterable.forEach((A a) -> aList.add(a)); //OK
}
}
ラムダのパラメーターを明示的に入力(A a) -> aList.add(a)
するとコードがコンパイルされる理由がわかりません。さらに、なぜそれがでIterable
はなく過負荷にリンクするのCustomIterable
ですか?
これに対する説明や、仕様の関連セクションへのリンクはありますか?
注:拡張iterable.forEach((A a) -> aList.add(a));
時にのみコンパイルしCustomIterable<T>
ますIterable<T>
(メソッドのフラットなオーバーロードによりCustomIterable
、あいまいなエラーが発生します)。
両方でこれを取得する:
- openjdkバージョン "13.0.2" 2020-01-14
Eclipseコンパイラ - openjdkバージョン "1.8.0_232"
Eclipseコンパイラ
編集:上記のコードは、Eclipseがコードの最後の行を正常にコンパイルしている間、mavenでビルドするとコンパイルに失敗します。