函数式接口在java中是指:有且仅有一个抽象方法的接口
函数式接口,即适用于函数式编程场景的接口。而java中的函数式编程体现就是Lambda,所以函数式接口就是可以适用于Lambda使用的接口。只有确保接口中有且仅有一个抽象方法,Java中的Lambda才能顺利地进行推导。
@FunctionalInterface注解
我们可以在任意函数式接口上使用@FunctionalInterface注解,这样做可以检查它是否是一个函数式接口,同时javadoc也会包含一条声明,说明这个接口是一个函数式接口。一旦使用该注解来定义接口,编译器将会强制检查该接口是否确实有且仅有一个抽象方法,否则将会报错。
自定义函数式接口
@FunctionalInterface
public interface MyFuctionInterface {
//public 和 abstract可以不写,编译器会自动加上
public abstract void method();
}
static void fun12(){
//匿名内部类方式创建
MyFuctionInterface mf = new MyFuctionInterface() {
@Override
public void method() {
System.out.println("匿名内部类方式");
}
};
//lambda方式
MyFuctionInterface mf2 = () -> System.out.println("lambda方式")
}
内置四大函数式接口
函数式接口 | 入参类型 | 返回类型 | 用途 |
---|---|---|---|
Consumer<T> 消费型接口 | T | void | 对类型为T的对象应用操作,包含方法:void accept(T t) |
Supplier<T> 供给型接口 | 无 | T | 返回类型为T的对象,包含方法:T get() |
Function<T,R> 函数型接口 | T | R | 对类型为T的对象应用操作,并返回结果为R类型的对象。包含方法:R apply(T t) |
Predicate<T> 断言型接口 | T | boolean | 确定类型为T的对象是否满足某约束,并返回boolean值。包含方法:boolean test(T t) |
Consumer
Consumer<T>
包含方法:
- void accept(T t):对给定的参数执行此操作
- default Consumer < T > andThen(Consumer after):返回一个组合的Consumer,依次执行此操作,然后执行after操作
andThen源码
default Consumer<T> andThen(Consumer<? super T> after) {
Objects.requireNonNull(after);
return (T t) -> { accept(t); after.accept(t); };
}
使用示例:
static void fun14(String name){
Consumer<String> con1 = (str) -> System.out.println(str+"-con1");
Consumer<String> con2 = (str) -> System.out.println(str+"-con2");
con1.accept(name);
con1.andThen(con2).accept(name);
}
输出:
jack-con1
jack-con1
jack-con2
Supplier
Supplier<T>
包含方法:
- T get():获得结果,该方法不需要参数,他会按照某种实现逻辑(由Lambda表达式实现)返回一个数据
- Supplier< T >接口也被称为供给型接口,如果我们指定了接口的泛型是什么类型,那么接口中的get方法就会产生什么类型的数据供我们使用
static void fun15(){
String result = getSup(()->"a supplier");
System.out.println(result);
}static String getSup(Supplier<String> sup){
return sup.get();
}
输出:
a supplier
Function
Function<T,R>
常用方法:
- R apply(T t):对类型为T的对象应用操作,并返回结果为R类型的对象
- default< V >:Function andThen(Function after):返回一个组合函数,首先将该函数应用于输入,然后将after函数应用于结果
- default < V > Function<V, R> compose(Function<? super V, ? extends T> before):返回一个组合函数,该函数首先将before函数应用于其输入,然后将此函数应用于结果
andThen源码
default <V> Function<T, V> andThen(Function<? super R, ? extends V> after) {
Objects.requireNonNull(after);
return (T t) -> after.apply(apply(t));
}
compose源码
default <V> Function<V, R> compose(Function<? super V, ? extends T> before) {
Objects.requireNonNull(before);
return (V v) -> apply(before.apply(v));
}
示例:
static void fun16(){
String res = function("aaa",str -> str.length(),i -> i+"--func2");
System.out.println(res);
}
static String function(String str,Function<String,Integer> func1,Function<Integer,String> func2){
System.out.println(func1.apply(str));
return func1.andThen(func2).apply(str);
}
输出:
3
3--func2
Predicate
常用方法
boolean test(T t):对给定的参数进行判断(判断逻辑由Lambda表达式实现),返回一个布尔值
default Predicate< T > negate():返回一个逻辑的否定,对应逻辑非
default Predicate< T > and(Predicate<? super T> other):返回一个组合判断,对应短路与
default Predicate< T > or(Predicate<? super T> other):返回一个组合判断,对应短路或
isEqual(Object targetRef):测试两个参数是否相等
示例
tatic void fun17(){
boolean res = pred("bbb", str -> str.equals("aca"), str -> str.equals("bbb"));
System.out.println(res);
}
static boolean pred(String s, Predicate<String> pre1,Predicate<String> pre2){
return pre1.or(pre2).test(s);
}