您的位置:

函数式接口详解

Java 8 引入了新的概念"函数式接口",用来支持Lambda表达式。函数式接口是指只有一个抽象方法的接口,即SAM接口(Single Abstract Method Interface)。在函数式接口中,可以定义多个默认方法和静态方法,但只能有一个抽象方法。

一、定义函数式接口

函数式接口的定义非常简单,只需要在接口上加上@FunctionalInterface注解即可,如下所示:

@FunctionalInterface
public interface MyFunctionalInterface {
  void apply(String str);
}

在这个接口中,我们定义了一个抽象方法apply(),接受一个字符串参数。注意到这里使用了@FunctionalInterface注解,这是为了方便编译器检查这个接口是否只包含一个抽象方法。

二、使用函数式接口

使用函数式接口可以通过Lambda表达式、方法引用等方式来提供实现。需要注意的是,提供的实现方法的参数和返回值必须与抽象方法一致。

1. Lambda表达式

Lambda表达式可以用来快速实现函数式接口,例如:

MyFunctionalInterface myLambda = (str) -> System.out.println(str);
myLambda.apply("Hello Lambda!");

在这个例子中,我们定义了一个Lambda表达式,并创建了一个函数式接口实例,再调用apply()方法,输出"Hello Lambda!"。

2. 方法引用

另外一种实现函数式接口的方式是使用方法引用,例如:

MyFunctionalInterface myMethodRef = System.out::println;
myMethodRef.apply("Hello Method Reference!");

这个例子使用了System类的静态方法println(),并将它作为方法引用传递给MyFunctionalInterface接口的实例。

三、函数式接口的分类

Java 8为我们提供了众多的函数式接口,这些接口被分为四类:函数型接口、供给型接口、消费型接口和断言型接口,下面我们来分别介绍。

1. 函数型接口

函数型接口(Function),它接受一个参数并且返回一个结果。如下所示:

@FunctionalInterface
interface Function {
    R apply(T t);
}

  

其中T表示输入类型,R表示输出类型。例如:

Function func = (x) -> x.toString();
System.out.println(func.apply(10));

  

这个例子定义了一个函数式接口func,接受一个整型参数并返回一个字符串类型的结果。在Lambda表达式中,我们将整型参数转换为字符串类型返回。

2. 供给型接口

供给型接口(Supplier),它不接受参数,但返回一个结果。如下所示:

@FunctionalInterface
interface Supplier {
    T get();
}

  
例如:
Supplier supplier = () -> "Hello World!";
System.out.println(supplier.get());

  

这个例子定义了一个供给型接口supplier,它返回一个固定的字符串"Hello World!"。

3. 消费型接口

消费型接口(Consumer),它接受一个参数但没有返回值。如下所示:

@FunctionalInterface
interface Consumer {
    void accept(T t);
}

  

例如:

Consumer consumer = (str) -> System.out.println(str);
consumer.accept("Hello Consumer!");

  

这个例子定义了一个消费型接口consumer,接受一个字符串参数并将其打印到控制台上。

4. 断言型接口

断言型接口(Predicate),它接受一个参数并返回一个布尔类型的值。如下所示:

@FunctionalInterface
interface Predicate {
    boolean test(T t);
}

  
例如:
Predicate predicate = (x) -> x > 0;
System.out.println(predicate.test(-2));
System.out.println(predicate.test(2));

  

这个例子定义了一个断言型接口predicate,接受一个整型参数并返回一个布尔类型的值,表示这个整数是否大于0。我们在Lambda表达式中,对输入参数进行判断,返回true或false。

四、总结

本文详细介绍了函数式接口的定义、使用方法和分类,同时也给出了相应的代码示例。函数式接口是支持Lambda表达式的基础,掌握函数式接口对于掌握Java 8的Lambda表达式来说至关重要。