如果作为一个语句编写,则作为Predicate接口的方法组合的Lambda不会编译
这两种lambda创造方式有什么区别? 为什么不编译第一个?
Predicate predicate = Predicate.isEqual(0).or(Predicate.isEqual(1));
给出: 错误 :不兼容的类型: Predicate
不能转换为Predicate = Predicate.isEqual(0).or(Predicate.isEqual(1));
Predicate pred21 = Predicate.isEqual(0); Predicate pred22 = pred21.or(Predicate.isEqual(1));
这个有效。
在isEqual
方法调用之前添加
应该有帮助:
Predicate predicate = Predicate. isEqual(0).or(Predicate.isEqual(1));
这种编译器行为背后的原因:
-
isEqual
是一个返回Predicate
的静态generics方法(无论其输入参数的实际类型是什么),因此在调用方法时返回Predicate
而不明确指定返回类型。 -
or
也是一个静态generics方法,但它返回一个由相同类型参数化的谓词,作为其输入参数(即Predicate
)。
问题与推理在Java中的工作方式有关:它取决于目标。
这里 :
Predicate predicate = Predicate.isEqual(0) .or(Predicate.isEqual(1));
or(Predicate.isEqual(1))
返回的类型or(Predicate.isEqual(1))
取决于Predicate.isEqual(0)
(最近的目标)返回的类型,但是这个调用没有指定任何其他类型作为返回。
所以Object
由or(Predicate.isEqual(1))
返回,因为方法isEqual()
将T
定义为不带任何通配符的返回类型:
static Predicate isEqual(Object targetRef) {
要解决您的问题,您确实需要指定第一次调用的返回类型,以便允许链式调用推断出正确的类型: Integer
。
Predicate predicate = Predicate. isEqual(0) .or(Predicate.isEqual(1));
这是因为
Predicate.isEqual(0)
有这个签名:
static Predicate isEqual(Object targetRef)
如果您不键入Predicate
它会推断它。
要键入它,您可以键入返回类型
Predicate pred21 = Predicate.isEqual(0);
或者输入类似的电话
Preicate.isEqual
看看签名:
static Predicate isEqual(Object targetRef)
在第一个示例中,编译器无法猜测generics类型参数,因此它返回Predicate
。
在一行中键入它的正确方法是指定类型参数
Predicate predicate = Predicate. isEqual(0).or(Predicate.isEqual(1));