java代码(14) --Java8函数式接口


 Java8函数式接口


之前有关JDK8的Lambda表达式 Java代码(1)--Java8 Lambda

函数式接口可以理解就是为Lambda服务的,它们组合在一起可以让你的代码看去更加简洁

一、概念

1、什么是函数式接口

  所谓函数式接口,当然首先是一个接口,然后就是在这个接口里面 只能有一个抽象方法

有关函数式接口,有个专门的注解叫  @FunctionalInterface ,该注解主要特点有:

    1、该注解只能标记在“有且仅有一个抽象方法”的接口上,表示函数式接口
    2、JDK8接口中的静态方法和默认方法,都不算抽象方法
    3、接口默认继承java.lang.Object,所以如果接口显示声明覆盖了Object中的方法,那么也不算抽象方法
    4、允许java.lang.Object中的public方法
    5、该注解不是必须的,如果一个接口符合‘函数式编程’定义,那么加不加该注解都没有影响,加上该注解能够让编译器更好的检查,如果编写的不是函数式接口,但是加上了@FunctionalInterface那么编译器会报错

正确示例

/**
 * 函数式接口注解
 */
@FunctionalInterface
public interface PersonInterface {
    /**
     * 1、仅有一个抽象方法
     */
    void say();
    /**
     * 2、java.lang.Object中的方法不算
     */
    @Override
    boolean equals(Object object);
    /**
     * 3、java8接口才可以默认的方法实现,前提是方法名称必须使用default关键字修饰
     */
    default void defaultMethod(){
        System.out.println("hello");
    }
    /**
     * 4、静态方法
     */
    static void staticMethod(){
        
    }
}

错误示例

    /**
     * 函数式接口注解
     */
    @FunctionalInterface  //编译直接报错
    public  interface Test{
     
      //1抽象方法
        void say();

     //2抽象方法
       void jump();
    }

加上@FunctionInterface,就代表该接口是函数式接口,只能有一个抽象方法,如果多个编译直接报错

3、为什么只能有一个抽象方法

其实这个问题很好去理解,上面说了函数式接口主要是为Lambda语法服务的,为了让代码看上去更简洁

下面通过示例来说明

 public static void main(String[] args) {
        PersonInterface inter =() -> System.out.println("说什么呢?");
        inter.say();
        //输出:说什么呢?
        
    }

通过函数式接口+Lambda表达式让代码看上去变得简洁的,关键点在于

 ()->{} 就代表对say()方法的重写

如果有多个抽象方法,那么()->{ } 这种写法,编译器就不知道这个重写哪个方法了,所以这就是为什么只能有一个抽象方法的原因

二、综合示例

这里在举一个综合示例,来方便理解它们

自定义函数式接口

/**
 * 自定义函数TestFunction 提供handler接口,传入的是A,返回的是B
 * @param <A>
 * @param <B>
 */
@FunctionalInterface
public interface MyFunction<A,B> {
    B handler(A a ,A a1);
}

Student对象

@Data
@AllArgsConstructor
@ToString
public class Student {
    //姓名
    private String name;
    //年龄
    private Integer age;
}

测试类

 public static void main(String[] args) {
        //1.求和,传入integer返回integer类型
        MyFunction<Integer,Integer> myFunction=(x,y)->{
            return x+y;
        };
        Integer count=myFunction.handler(5,10);
        System.out.println("输出总和为:"+count);

        //2、求和传入integer返回String类型
        MyFunction<Integer,String> myFunction1=(x,y)->{
            return x+"+"+y+"="+(x+y);
        };
        System.out.println(myFunction1.handler(5,10));

        //3、对象处理过滤对象
        List<Student> students= Arrays.asList(new Student("小明",3),new Student("小白",13),new Student("小黄",19));
        MyFunction<Integer,List<Student>> myFunction2=(x,y)->{
            List<Student> studentList=students.stream().filter(student -> student.getAge()>x && student.getAge()<y).collect(Collectors.toList());
            return studentList;
        };
        List<Student> list=myFunction2.handler(5,15);
        list.forEach(x-> System.out.println(x));
    }

运行结果:

 从运行结果可以很明显看出,集合对象经过过滤只剩下一个满足条件的了。

原文地址:https://www.cnblogs.com/zhenbian/p/13031252.html