根据 JLS 15.27.2 lambda 主体与周围上下文具有相同的范围,我想知道是否有特定原因说明为什么 lambda 实现的接口(interface)中的默认方法在主体内也不可用?此限制是否启用了一些优化或只是为了保持过载规则简单?
我今天正在制作一些 Java 8 API 的原型(prototype),当我遇到这个限制时,我非常失望,因为使用默认方法可以让我以非常优雅和非侵入性的方式实现该 API。
通过静态导入或多或少可以实现同样的优雅,但这会导致“污染”命名空间。
是否有可能取消此限制?
最佳答案
默认方法对 lambda 不可用,因为在将 lambda 分配给功能类型之前尚未为其指定类型。例如,lambda
s -> s.isEmpty()
可以分配给 java.util.function.Predicate
或 com.google.common.base.Predicate
。出于这个原因,它无法访问 java.util.function.Predicate
的默认方法,直到它被实际分配给 java.util.function.Predicate
直接分配给 java.util.function.Predicate
,通过将 lambda 作为 java.util.function.Predicate
参数传递,从返回类型为的函数返回它java.util.function.Predicate
,或者像这样简单地将其转换为 java.util.function.Predicate
:
((Predicate<String>) s -> s.isEmpty()).negate(); // negate is a default method on Predicate
可以将其类比为装箱 int
值。 Integer
的方法不能在文字整数值上调用,但一旦将整数值分配给 Integer
类型,就可以调用它的方法。
关于java - 在 lambda 表达式中使用默认方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36628152/