【发布时间】:2016-10-28 08:20:16
【问题描述】:
在Java 8 lambdas, Function.identity() or t->t 找到的答案似乎暗示Function.identity() 几乎总是等同于t -> t。但是,在下面看到的测试用例中,将 t -> t 替换为 Function.identity() 会导致编译器错误。这是为什么呢?
public class Testcase {
public static <T, A, R, K, V> Collector<T, A, R> comparatorOrdering(
Function<? super T, ? extends K> keyMapper,
Function<? super T, ? extends V> valueMapper,
Comparator<? super K> keyComparator,
Comparator<? super V> valueComparator) {
return null;
}
public static void main(String[] args) {
Map<Integer, String> case1 = Stream.of(1, 2, 3).
collect(comparatorOrdering(t -> t, t -> String.valueOf(t),
Comparator.naturalOrder(), Comparator.naturalOrder()));
Map<Integer, String> case2 = Stream.of(1, 2, 3).
collect(comparatorOrdering(Function.identity(), t -> String.valueOf(t),
Comparator.naturalOrder(), Comparator.naturalOrder()));
}
}
案例 1 编译得很好,但案例 2 失败:
method comparatorOrdering in class Testcase cannot be applied to given types;
collect(comparatorOrdering(Function.identity(), t -> String.valueOf(t),
required: Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>
found: Function<Object,Object>,(t)->Strin[...]Of(t),Comparator<T#2>,Comparator<T#3>
reason: inferred type does not conform to upper bound(s)
inferred: Object
upper bound(s): Comparable<? super T#4>,T#4,Object
where T#1,A,R,K,V,T#2,T#3,T#4 are type-variables:
T#1 extends Object declared in method <T#1,A,R,K,V>comparatorOrdering(Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>)
A extends Object declared in method <T#1,A,R,K,V>comparatorOrdering(Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>)
R extends Object declared in method <T#1,A,R,K,V>comparatorOrdering(Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>)
K extends Object declared in method <T#1,A,R,K,V>comparatorOrdering(Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>)
V extends Object declared in method <T#1,A,R,K,V>comparatorOrdering(Function<? super T#1,? extends K>,Function<? super T#1,? extends V>,Comparator<? super K>,Comparator<? super V>)
T#2 extends Comparable<? super T#2>
T#3 extends Comparable<? super T#3>
T#4 extends Comparable<? super T#4> declared in method <T#4>naturalOrder()
我的环境是 Windows 10,64 位,Oracle JDK build 1.8.0_92-b14。
更新:看到这是在 ecj 下编译的,我有一个后续问题:这是 javac 中的错误吗? JLS对此案有什么看法?
【问题讨论】:
-
你能分享一些关于你的环境的细节吗?这对我来说编译得很好。
-
我可以用 Java 1.8.0_92 重现这个。 (OpenJDK)
-
@StephenC 哪个版本的 1.8.0_92?我用的是 1.8.0_92-b14 不能复现。
-
$ java -version==>openjdk version "1.8.0_92" OpenJDK Runtime Environment (build 1.8.0_92-b14) OpenJDK 64-Bit Server VM (build 25.92-b14, mixed mode).... 在 Fedora Linux 上 -
这个错误在javac中不是在ecj中是可以重现的,所以eclipse中没有错误说明不了太多。
标签: java generics reification