泛型方法无法使用Lambda表达式

先说结论,Java中的泛型方法无法使用Lambda表达式
做个简单的Demo
首先创建一个存储接口Storable

public interface Storable<T> {
    <V,K> T store();
}

其次,创建一个Repository类,其中的execute方法将使用到前面的存储接口

public class Repository {
    public <T> String execute(Storable<T> storable ){
        return "I am storing";
    }
}

接下来我们来创建测试类

public class Test {
    public static void main(String[] args) {
        Repository repository = new Repository();
        // 不适用Lambda表达式
        System.out.println(repository.execute(new Storable<String>() {
            @Override
            public <V, K> String store() {
                return "I am not Lambda";
            }
        }));
        // 适用Lambda表达式
        // 报错,Lambda没办法作用于泛型方法
//        System.out.println(repository.execute(() -> {
//            return null;
//        });

}

在使用Lambda表达式中,报了一个"Target method is generic"的提示。
为什么Lambda表达式没办法使用泛型方法,其实很简单,Lambda表达式是一种函数式编程,作用就是重写接口的唯一方法,也可以看做是声明这个方法,而泛型方法中的类型参数,是在声明方法的时候使用的,而只有在调用方法的时候才确定具体的类型,目前Lambda语法是没办法兼有泛型方法的类型参数,我们来分别看一下两者的声明:

  • Lambda表达式语法:
    (parameters) -> experssion
    或者
    (parameters) -> { statements; }
  • 泛型方法表达式
    public <E,G> void test(Map<E,G> map){ }

官方文档https://docs.oracle.com/javase/specs/jls/se8/html/jls-15.html#jls-15.27.3也提到了

A lambda expression is congruent with a function type if all of the following are true:

  • The function type has no type parameters.

如果下面提到的点都能够成立,那么Lambda表达式是能够和一个函数类型相适应的:

  • 函数类型不能有类型参数

其实没办法使用Lambda表达式也不是什么大事,直接写该接口的匿名类也可以的。

附上跟舍友聊天的记录,本博客来源是学习Redis中遇到的一个小问题
在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/Cap220590/article/details/107786032