概述

函数式接口(Functional Interface)即只有一个抽象方法的接口。

Runnable接口就是一个函数式接口,Runnable接口中只包含一个抽象的run()方法,并且在接口上标注了一个@FuncationInterface注解,用来标识一个函数式接口

  1. @FunctionalInterface
  2. public interface Runnable {
  3. /**
  4. * When an object implementing interface <code>Runnable</code> is used
  5. * to create a thread, starting the thread causes the object's
  6. * <code>run</code> method to be called in that separately executing
  7. * thread.
  8. * <p>
  9. * The general contract of the method <code>run</code> is that it may
  10. * take any action whatsoever.
  11. *
  12. * @see java.lang.Thread#run()
  13. */
  14. public abstract void run();
  15. }

定义创建函数式接口

  • 定义一个抽象方法:注意,接口中只能有一个抽象方法;
  • 在接口上标记@FunctionalInterface 注解,当然也可以不标记,注解的作用主要是编辑器就自动检测定义的函数式接口是否有问题。

创建函数式接口

  1. @FunctionalInterface
  2. public interface FunctionalInterfaceTest {
  3. void foo();
  4. }

测试函数式接口

  1. public class FunctionalInterfaceDemo {
  2. public static void main(String[] args) {
  3. FunctionalInterfaceTest functionalInterfaceTest = new FunctionalInterfaceTest() {
  4. @Override
  5. public void foo() {
  6. System.out.println("hello world");
  7. }
  8. };
  9. functionalInterfaceTest.foo();
  10. // lambda
  11. FunctionalInterfaceTest lambdaTest = ()->System.out.println("hello lambda");
  12. lambdaTest.foo();
  13. }
  14. }

使用Lambda表达式来创建,这种方法相较匿名内部类更加简洁,

内置函数式接口

JDK 8 之后新增了一个函数接口包 java.util.function 这里面包含了我们常用的一些函数接口:

接口 参数 返回类型 说明
Predicate T boolean 接受一个输入参数 T,返回一个布尔值结果
Supplier None T 无参数,返回一个结果,结果类型为 T
Consumer T void 代表了接受一个输入参数 T 并且无返回的操作
Function T R 接受一个输入参数 T,返回一个结果 R
UnaryOperator T T 接受一个参数为类型 T, 返回值类型也为 T
BinaryOperator (T,T) T 代表了一个作用于于两个同类型操作符的操作,并且返回了操作符同类型的结果

Consumer

Comsumer消费型接口: 表示接受单个输入参数但不返回结果的操作,包含方法:void accept(T t),可以理解为消费者,只消费(接收单个参数)、不返回(返回为 void);

  1. public class ConsumerDemo {
  2. public static void main(String[] args) {
  3. Consumer<String> consumer = s->System.out.println(s);
  4. consumer.accept("hello world");
  5. }
  6. }

Supplier

Supplier供给型接口:表示结果的供给者,包含方法T get(),可以理解为供给者,只提供(返回T类型对象)、不消费(不接受参数);

  1. // Supplier接口源码
  2. @FunctionalInterface
  3. public interface Supplier<T> {
  4. /**
  5. * Gets a result.
  6. *
  7. * @return a result
  8. */
  9. T get();
  10. }

java.util.function.Supplier 接口仅包含一个无参的方法: T get() 。用来获取一个泛型参数指定类型的对象数据。由于这是一个函数式接口,这也就意味着对应的Lambda表达式需要“对外提供”一个符合泛型类型的对象数据

  1. public class SupplierDemo {
  2. public static void main(String[] args) {
  3. Supplier<String> supplier = () -> "hello world";
  4. String s = supplier.get();
  5. System.out.println(s);
  6. }
  7. }

Function

Function函数型接口:表示接受一个T类型参数并返回R类型结果的对象,包含方法R apply(T t);

  1. @FunctionalInterface
  2. public interface Function<T, R> {
  3. R apply(T t);
  4. ......
  5. }

apply

Function 接口中最主要的抽象方法为: R apply(T t) ,根据类型T的参数获取类型R的结果。 使用的场景例如:将 String 类型转换为 Integer 类型。

  1. public class FunctionApplyDemo {
  2. public static void main(String[] args) {
  3. Function<String, Integer> f = s -> Integer.parseInt(s);
  4. int num = f.apply("2");
  5. // 5
  6. System.out.println(num + 3);
  7. }
  8. }

andThen

andThen 方法用来进行组合操作。JDK源代码如:

  1. default <V> Function<T, V> andThen(Function<? super R, ? extends V> after) {
  2. Objects.requireNonNull(after);
  3. return (T t) -> after.apply(apply(t));
  4. }

eg:

  1. public class FunctionAndThenDemo {
  2. public static void main(String[] args) {
  3. method(
  4. str -> Integer.parseInt(str) + 2,
  5. i -> i *= 3
  6. );
  7. }
  8. private static void method(Function<String, Integer> one, Function<Integer, Integer> two) {
  9. int num = one.andThen(two).apply("1");
  10. //(1+2)*3+1
  11. System.out.println(num + 1);
  12. }
  13. }
  1. public class FunctionDemo {
  2. public static void main(String[] args) {
  3. String str = "a-1";
  4. int age = getNum(
  5. str,
  6. s -> s.split("-")[1],
  7. s -> Integer.parseInt(s),
  8. n -> n += 2
  9. );
  10. System.out.println(age);
  11. }
  12. private static int getNum(String str,
  13. Function<String, String> one,
  14. Function<String, Integer> two,
  15. Function<Integer, Integer> three) {
  16. return one.andThen(two).andThen(three).apply(str);
  17. }
  18. }

Predicate

某种类型的数据进行判断,从而得到一个boolean值结果。这时可以使用java.util.function.Predicate 接口。
Predicate断言型接口:确定T类型的对象是否满足约束,并返回boolean值,包含方法boolean test(T t)。

test

Predicate 接口中包含一个抽象方法: boolean test(T t) 。用于条件判断的场景:

逻辑关系。

与 (and) 、或 (or) 、非 (negate) 的默认方法