Day 28
1. 函数式接口
1.1 概述
如果说一个接口只有一个方法,而且干方法是一个缺省属性为abstract方法,该接口称之为函数式接口。
可以直接使用JDK1.8新特征,Lambda表达式来使用
Lambda表达式对比匿名内部类
1. 简化了代码结构
2. 节约了内存资源
3. 让程序员更加关注我要做什么,而不是为了做什么需要完成什么
1.2 @FunctionalInterface使用
类似于
@Override 开启代码重写格式严格检查
1.3 使用函数式接口
代码中使用函数式接口
1. 让程序的目的性更强
2. 提供复用,普适性的价值
3. 节约资源
2. 函数式编程思想
2.1 Lambda延迟执行
日志是否保存会存在等级限制
这里需要一个函数式接口,返回值类型是String类型,其他的无所谓。
public class Demo2 {
public static void main(String[] args) {
String msg1 = "异常位置XXX,";
String msg2 = "异常问题XXX,";
String msg3 = "异常时间XXX";
log(Level.LOWER, () -> {
System.out.println("Lambda表达式执行!!!");
return msg1 + msg2 + msg3;
});
}
public static void log(Level level, LogMessage lm) {
if (Level.HIGH == level) {
System.err.println(lm.returnLogMessage());
}
}
public static void testEnum(int level) {
if (Level.HIGH.getStatus() == level) {
}
}
}
2.2 Lambda作为方法参数和返回值
Java中提供的比较接口Comparator<T>
利用一些返回值作为方法中操作的调节
public interface Comparator<T> {
int compare(T o1, T o2);
}
3. Java中提供的常用函数式接口
3.1 JDK常用函数式接口概述
java.util.function包名 。提供了很多函数式接口
规范了一些操作,提升了开发效率,更加专注于目的性!!!
Supplier<T> 生产者, 返回一个指定类型的数据
Consumer<T> 消费者, 消耗一个指定类型的数据
Predicate<T> 判断调节,过滤使用
Function<T,R> 类型转换,根据你指定的类型T, 转换成对应类型R
3.2 Supplier 生产者,返回一个指定的数据类型
java.util.function.Supplier<T>
有且只有一个方法
T get();
不需要参数,返回指定T类型数据
什么都不吃,挤的都是输出。。。
package com.qfedu.c_supplier;
import com.qfedu.b_lambda.Level;
import java.util.function.Supplier;
public class Demo1 {
public static void main(String[] args) {
String msg1 = "异常位置XXX,";
String msg2 = "异常问题XXX,";
String msg3 = "异常时间XXX";
log(Level.HIGH, () -> {
System.out.println("Lambda表达式执行!!!");
return msg1 + msg2 + msg3;
});
log(Level.HIGH, () -> msg1 + msg2 + msg3);
}
public static void log(Level level, Supplier<String> supplier) {
if (Level.HIGH == level) {
System.err.println(supplier.get());
}
}
}
引出满足更多普适性代码的函数式接口使用方式
package com.qfedu.c_supplier;
import java.util.function.Supplier;
public class Demo3 {
public static void main(String[] args) {
Integer[] array = {1, 3, 5, 7, 9, 2, 4, 6, 8, 10};
Integer max = getMax(array, () -> {
Integer temp = array[0];
for (int i = 1; i < array.length; i++) {
if (temp < array[i]) {
temp = array[i];
}
}
return temp;
});
System.out.println(max);
System.out.println("-------------------------------------------");
Person[] persons = {new Person(1, "骚磊", 16),
new Person(2, "老黑", 66),
new Person(3, "老付", 36),
new Person(4, "老高", 26),
new Person(5, "污云", 96),
new Person(6, "帅栋", 106)
};
Person max1 = getMax(persons, () -> {
Person p = persons[0];
for (int i = 1; i < persons.length; i++) {
if (p.getAge() < persons[i].getAge()) {
p = persons[i];
}
}
return p;
});
System.out.println(max1);
}
public static <T> T getMax(T[] arr, Supplier<T> sup) {
return sup.get();
}
}
3.3 Consumer消费者,处理数据
Consumer<T>
操作使用的方式是
void accept(T t);
根据接口指定的数据类型接收对应数据,进行处理和消费,对外没有任何的返回
至于处理的过程,展示,处理,计算。。。
package com.qfedu.d_consumer;
import java.util.function.Consumer;
public class Demo1 {
public static void main(String[] args) {
testConsumer("宫保鸡丁,番茄牛腩,酱牛肉,黄焖鸡米饭", (str) -> {
String[] split = str.split(",");
for (String s : split) {
System.out.println(s);
}
});
}
public static void testConsumer(String str, Consumer<String> consumer) {
consumer.accept(str);
}
}
andThen
package com.qfedu.d_consumer;
import java.util.function.Consumer;
public class Demo2 {
public static void main(String[] args) {
testAndThen("郑州加油!!!中国加油!!!",
(str) -> System.out.println(str)
,
(str) -> System.err.println(str)
);
}
public static void testAndThen(String str, Consumer<String> con1, Consumer<String> con2) {
con1.andThen(con2).accept(str);
}
}
3.4 Predicate 判断数据是否合适,返回true/false
Predicate<T>一般用于调节判断,过滤数据的方法
函数式接口中指定的方法
boolean test(T t);
处理T类型数据,返回boolean true / false
package com.qfedu.e_predicate;
import java.util.function.Predicate;
public class Demo1 {
public static void main(String[] args) {
boolean b = testPredicate("郑州奥力给!!!中国奥力给!!!",
(str) -> {
return str.contains("加油");
});
System.out.println("ret : " + b);
System.out.println("---------------------------");
testPredicate("郑州奥力给!!!中国奥力给!!!", str -> str.contains("加油"));
}
public static boolean testPredicate(String str, Predicate<String> pre) {
return pre.test(str);
}
}
and 与
package com.qfedu.e_predicate;
import java.util.function.Predicate;
public class Demo2 {
public static void main(String[] args) {
boolean ret = testAnd("赶紧复工吧,不要搞事情了!!!",
str -> str.length() > 5,
str -> str.startsWith("赶紧"));
System.out.println(ret);
}
public static boolean testAnd(String str, Predicate<String> pre1, Predicate<String> pre2) {
return pre1.and(pre2).test(str);
}
}
or 或
package com.qfedu.e_predicate;
import java.util.function.Predicate;
public class Demo3 {
public static void main(String[] args) {
boolean ret = testOr("国家之强大,国外人羡慕不得~~",
str -> str.length() < 10,
str -> str.contains("国家"));
System.out.println(ret);
}
public static boolean testOr(String str, Predicate<String> pre1, Predicate<String> pre2) {
return pre1.or(pre2).test(str);
}
}
negate 非
package com.qfedu.e_predicate;
import java.util.function.Predicate;
public class Demo4 {
public static void main(String[] args) {
boolean ret = testNegate("疫情总会过去的!!!",
str -> str.length() < 5);
System.out.println(ret);
}
public static boolean testNegate(String str, Predicate<String> pre) {
return pre.negate().test(str);
}
}
ArrayList中使用Predicate删除指定数据
package com.qfedu.e_predicate;
import com.qfedu.c_supplier.Person;
import java.util.ArrayList;
public class Demo5 {
public static void main(String[] args) {
ArrayList<Person> list = new ArrayList<>();
list.add(new Person(1, "骚磊", 16));
list.add(new Person(2, "老黑", 66));
list.add(new Person(3, "老付", 36));
list.add(new Person(4, "老高", 26));
list.add(new Person(5, "污云", 96));
list.add(new Person(6, "帅栋", 96));
list.removeIf(person -> person.getAge() > 40 && person.getId() > 3);
System.out.println(list);
}
}
3.5 Function<T,R> 类型转换
使用R apply(T t)
转换指定类型T到R
package com.qfedu.f_function;
import com.qfedu.c_supplier.Person;
import java.util.function.Function;
public class Demo1 {
public static void main(String[] args) {
String change = change(10, i -> i + "");
System.out.println(change);
Person person1 = change("1,骚磊,16", str -> {
String[] split = str.split(",");
Person person = new Person();
person.setId(Integer.parseInt(split[0]));
person.setName(split[1]);
person.setAge(Integer.parseInt(split[2]));
return person;
});
System.out.println(person1);
}
public static String change(Integer i, Function<Integer, String> fun) {
return fun.apply(i);
}
public static Person change(String str, Function<String, Person> fun) {
return fun.apply(str);
}
}
andThen
package com.qfedu.f_function;
import java.util.function.Function;
public class Demo2 {
public static void main(String[] args) {
String s = testAndThen(10,
i -> i + "",
i -> i + "测试");
System.out.println(s);
}
public static String testAndThen(int i, Function<Integer, String> fun1, Function<String, String> fun2) {
return fun1.andThen(fun2).apply(i);
}
}