功能接口继承怪癖
Functional Interface Inheritance Quirk
我有一个我已经使用了一段时间的自定义界面,看起来像这样:
public interface Function<T, R> {
R call(T input);
}
我想用 Java 的 Function
as well as Guava's Function
, while keeping it a FunctionalInterface
来改进这个界面。我以为我的安排很完美:
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
两个超接口都声明了相同的apply()
方法,我的接口已经实现了,只留下抽象的call()
方法。奇怪的是,它不会编译,告诉我
Invalid '@FunctionalInterface' annotation; Function<T,R> is not a functional interface
还是陌生人,以下变体编译得很好:
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
@FunctionalInterface
public interface Function<T, R> extends
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
@Override
R apply(T input);
}
是否有第一个版本无法编译的原因?
如评论中所述,使用 oracle 编译器可以很好地编译它。
这是一个日食错误。
等待错误修复,我个人将删除注释 @FunctionalInterface
(您的第三个变体):
public interface Function<T, R>
extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
此解决方案的主要不便之处在于 eclipse 编译器错误阻止将 Function
用作 lambda target type。
如果您真的想在 Function
上保留 @FunctionalInterface
,一个(丑陋的)解决方法可能是引入一个中间接口:
public interface AdapterFunction<T, R>
extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
@Override
default R apply(T input) {
return null;
}
}
并让你的 Function
扩展这个 AdapterFunction
:
@FunctionalInterface
public interface Function<T, R>
extends
AdapterFunction<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
在这种情况下,Function
也是 eclipse 的有效目标类型:
Function<String, Object> function = st -> st.toString();
我有一个我已经使用了一段时间的自定义界面,看起来像这样:
public interface Function<T, R> {
R call(T input);
}
我想用 Java 的 Function
as well as Guava's Function
, while keeping it a FunctionalInterface
来改进这个界面。我以为我的安排很完美:
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
两个超接口都声明了相同的apply()
方法,我的接口已经实现了,只留下抽象的call()
方法。奇怪的是,它不会编译,告诉我
Invalid '@FunctionalInterface' annotation; Function<T,R> is not a functional interface
还是陌生人,以下变体编译得很好:
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
@FunctionalInterface
public interface Function<T, R> extends
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
@FunctionalInterface
public interface Function<T, R> extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
@Override
R apply(T input);
}
是否有第一个版本无法编译的原因?
如评论中所述,使用 oracle 编译器可以很好地编译它。 这是一个日食错误。
等待错误修复,我个人将删除注释 @FunctionalInterface
(您的第三个变体):
public interface Function<T, R>
extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
此解决方案的主要不便之处在于 eclipse 编译器错误阻止将 Function
用作 lambda target type。
如果您真的想在 Function
上保留 @FunctionalInterface
,一个(丑陋的)解决方法可能是引入一个中间接口:
public interface AdapterFunction<T, R>
extends
java.util.function.Function<T, R>,
com.google.common.base.Function<T, R> {
@Override
default R apply(T input) {
return null;
}
}
并让你的 Function
扩展这个 AdapterFunction
:
@FunctionalInterface
public interface Function<T, R>
extends
AdapterFunction<T, R> {
R call(T input);
@Override
default R apply(T input) {
return call(input);
}
}
在这种情况下,Function
也是 eclipse 的有效目标类型:
Function<String, Object> function = st -> st.toString();