赞
踩
Lambda表达式好处:简化我们匿名内部类的调用
Java中使用Lambda表达式的规范,必须是为函数接口
JDK 1.8 版本以上有效
@FunctionalInterface 语法格式严格要求当前接口【有且只能有一个】尚未完成的 缺省属性为 public abstract 修饰方法。
Lambda 表达式和 方法引用使用的前提!!!
函数式接口一般用于方法的增强,直接作为方法的参数,实现【插件式编程】。
//代码示例
@FunctionalInterface
interface Test {
void test();
}
基本格式:(函数接口中方法的参数列表,只需写参数名称) -> { 方法体}
Lambda 表达式关注的是接口中方法的【返回值】和【参数】
使用Lambda 方法体中只有一条语句的情况下,在这时候我们不需要写{} 也可以不需要写return
接口设计
@FunctionalInterface
interface A {
void 方法名真的没有用();
}
方法设计
/**
* Lambda 测试方法,当前方法所需参数是 A 接口实例化对象,因为当前 A 接口
* 是一个函数式接口,可以使用 Lambda 表达式解决问题
*
* @param a 函数式接口 A
*/
public static void testLambda(A a) {
a.方法名真的没有用();
}
代码实现
public static void main(String[] args) { /* 1. 匿名内部类方式 */ testLambda(new A() { @Override public void 方法名真的没有用() { System.out.println("无参数返回值 匿名内部类对象方法实现"); } }); /* 2. Lambda 表达式实现 【分析】 void 方法名真的没有用(); 接口方法【返回值】 void 接口方法【参数】 无参数 Lambda 格式 () -> {大括号中无需返回值类型} */ testLambda(() -> { System.out.println("Lambda 表达式初体验"); }); // 【注意】Lambda 表达式有且只有一行代码,可以省略大括号 testLambda(() -> System.out.println("Lambda 表达式初体验")); // 方法引用方式 testLambda(Demo1::test); } public static void test() { System.out.println("方法引用"); }
接口设计
Consumer 消费者接口,数据最终处理接口,数据处理终止方法接口…因为当前接口中,数据有去无回
泛型可以在使用过程中,支持数据类型多样性,同时满足数据类型一致化要求!当前方法可以支持的数据类型满足所有情况。
@FunctionalInterface
public interface Consumer<T> {
/**
* 消费者接口,数据最终处理接口,数据处理终止方法接口,对应的方法要求
* 方法有参数无返回值
*
* @param t 泛型数据数据类型 T ,支持任意类型,在接口约束之后,要求符合
* 数据类型一致化要求
*/
void accept(T t);
}
方法设计
/**
* 有参数无返回 Lambda 测试方法,方法参数是 String 类型和针对于 String 类型
* 进行数据处理的 Consumer 接口,Consumer 接口可以传入实现类对象和 Lambda 表
* 达式
*
* @param str 目标处理的 String 字符串数据
* @param handle 已经约束为处理 String 类型数据的 Consumer 接口处理器
*/
public static void testLambda(String str, Consumer<String> handle) {
/*
需要方法外部提供针对于当前 String 字符串的处理能力。
处理能力通过 Consumer 接口传入
*/
handle.accept(str);
}
代码实现
public static void main(String[] args) { /* 1、匿名内部类 Low */ testLambda("孟州市炒面第一名", new Consumer<String>() { @Override public void accept(String t) { System.out.println(t); } }); /* 2. Lambda 表达式 【分析】 void accept(T t); ==> 泛型约束为 String ==> void accept(String t); 接口方法【返回值】 void 接口方法【参数】 1 个参数,String 类型 Lambda 格式 Lambda 小括号中的临时变量名称,没有数据类型体现,需要【联想】目标方法数据类型 只按照参数的个数定义临时小变量 (s) -> {大括号中无需返回值类型} Lambda 表达式临时变量 s 对应的数据类型为 String 类型 【联想可得】 */ testLambda("lambda表达式需要联想!!!", (s) -> { System.out.println(Arrays.toString(s.toCharArray())); }); /* Lambda 优化 1. 代码块有且只有一行,可以省略大括号 2. 小括号中有且只有一个 参数,可以省略小括号 【注意】 Lambda 承担的角色是一个针对于 String 字符串的处理器 */ testLambda("lambda表达式需要联想!!!", s -> System.out.println(Arrays.toString(s.toCharArray()))); // 方法引用 testLambda("lambda表达式需要联想!!!", System.out::println); testLambda("lambda表达式需要联想!!!", Demo2::test); } public static void test(String str) { System.out.println(str); }
生产者接口
巧妇难为无米之炊,使用的数据都是对应方法中的数据内容,利用方法【局部变量 Local Variable】
接口设计
@FunctionalInterface
interface Supplier<T> {
/**
* 无参数有返回值方法,泛型约束的是接口对应的返回值数据类型,要求
* 按照泛型约束返回对应的数据内容
*
* @return 返回一个数据,符合泛型约束
*/
T get();
}
方法设计
/**
* 当前方法要求返回一个字符串数据内容
*
* @param s Supplier 生产者,数据提供接口对应的参数
* @return 字符串数据
*/
public static String testLambda(Supplier<String> s) {
return s.get();
}
代码实现
public static void main(String[] args) { /* 1. 匿名内部类形式 */ String s = testLambda(new Supplier<String>() { @Override public String get() { return "这是一个字符串"; } }); System.out.println(s); /* /* 2. Lambda 表达式 【分析】 T get(); ==> 泛型约束为 String ==> String get(); 接口方法【返回值】 String 接口方法【参数】 无参数 Lambda 格式 () -> {必须返回一个 String 类型} return 关键字出马 */ String s1 = testLambda(() -> { return "这里也是一个字符串"; }); System.out.println(s1); /* Lambda 优化,只要 -> 之后是一个 字符串数据内容就可以满足当前 Lambda 所需 可以省略 return ,前提是当前 Lambda 有且只有一行代码 */ String s2 = testLambda(() -> "这里也是一个字符串"); System.out.println(s2); /* Lambda 内部使用使用方法局部变量 */ String str = "name=周冠宇&age=23&country=中国"; String s3 = testLambda(() -> { // str 是当前 main 方法局部变量,Lambda 内部可以直接使用 String[] split = str.split("&"); return split[0]; }); System.out.println(s3); // 方法引用 String s4 = testLambda(Demo3::test); System.out.println(s4); } public static String test() { return "Function Reference"; }
相关接口设计
比较器接口
@FunctionalInterface
interface Comparator<T> {
/**
* 比较器接口要求的方法,参数是泛型参数,用户指定类型
*
* @param o1 用户在使用接口时约束的泛型对应具体数据类型参数
* @param o2 用户在使用接口时约束的泛型对应具体数据类型参数
* @return 返回值为 int 类型,0 表示两个元素一致。
*/
int compare(T o1, T o2);
}
比较器案例代码
public class Demo5 { public static void main(String[] args) { Person[] array = new Person[5]; for (int i = 0; i < array.length; i++) { int age = (int) (Math.random() * 50); array[i] = new Person(i + 1, "张三", age, false); } /* Lambda 分析 boolean test(T t); ==> 泛型约束为 Person 类型 ==> boolean test(Person t); 方法返回值是 boolean 方法参数 1. 1 个 2. Person 类型 Lambda 格式 p -> {要求必须返回一个 boolean} */ Person[] temp = filterPersonArrayUsingPredicate(array, p -> p.getAge() > 10); for (Person person : temp) { System.out.println(person); } } /** * 过滤限定操作,利用 Predicate 过滤器接口限定数组内容 * * @param array Person 类型数组 * @param filter Predicate 过滤器参数 * @return 过滤限定之后的新数组 */ public static Person[] filterPersonArrayUsingPredicate(Person[] array, Predicate<Person> filter) { Person[] temp = new Person[array.length]; int count = 0; for (int i = 0; i < array.length; i++) { /* Predicate 接口提供的方法是 boolean test(T t); 目前泛型约束之后是 boolean test(Person t); 判断当前 Person 对象是否满足要求,如果满足,存储到 temp 数组中。 */ if (filter.test(array[i])) { temp[count++] = array[i]; } } return temp; } }
过滤器接口
// 过滤器接口,判断器接口,条件接口
@FunctionalInterface
interface Predicate<T> {
/**
* 过滤器接口约束的方法,方法参数是用户使用时约束泛型对应具体数据参数
* 返回值类型是 boolean 类型,用于条件判断,数据过来
*
* @param t 用户约束泛型对应的具体数据类型参数
* @return boolean 数据,判断结果反馈
*/
boolean test(T t);
}
过滤器接口案例代码
public class Demo5 { public static void main(String[] args) { Person[] array = new Person[5]; for (int i = 0; i < array.length; i++) { int age = (int) (Math.random() * 50); array[i] = new Person(i + 1, "张三", age, false); } /* Lambda 分析 boolean test(T t); ==> 泛型约束为 Person 类型 ==> boolean test(Person t); 方法返回值是 boolean 方法参数 1. 1 个 2. Person 类型 Lambda 格式 p -> {要求必须返回一个 boolean} */ Person[] temp = filterPersonArrayUsingPredicate(array, p -> p.getAge() > 10); for (Person person : temp) { System.out.println(person); } } /** * 过滤限定操作,利用 Predicate 过滤器接口限定数组内容 * * @param array Person 类型数组 * @param filter Predicate 过滤器参数 * @return 过滤限定之后的新数组 */ public static Person[] filterPersonArrayUsingPredicate(Person[] array, Predicate<Person> filter) { Person[] temp = new Person[array.length]; int count = 0; for (int i = 0; i < array.length; i++) { /* Predicate 接口提供的方法是 boolean test(T t); 目前泛型约束之后是 boolean test(Person t); 判断当前 Person 对象是否满足要求,如果满足,存储到 temp 数组中。 */ if (filter.test(array[i])) { temp[count++] = array[i]; } } return temp; } }
类型转换器接口
// 类型转换器接口
@FunctionalInterface
interface Function<T, R> {
R apply(T t);
}
代码实现
public class Demo6 { public static void main(String[] args) { String str = "开封有个包青天"; /* Lambda 分析 R apply(T t); ==> 泛型约束 T => String R => Integer Integer apply(String t); Lambda 格式 返回值类型 Integer 方法参数 1. 1个 2. String s -> {必须返回 int 类型数据} */ int i = testLambda(str, s -> s.length()); System.out.println(i); // 方法引用 int ret = testLambda("邠州有个范仲淹", Demo6::test); System.out.println(ret); } public static int testLambda(String str, Function<String, Integer> fun) { return fun.apply(str); } public static int test(String str) { return str.length(); } }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。