1、为什么使用lambda表达式
Lambda是一个匿名函数,可以理解为一段可以传递的代码,将代码像数据一样进行传递,可以写出更加简介、更加灵活的代码。作为一宗更紧凑的代码风格,使Java的语言表达能力得到了提升
2、Lambda表达式的基础语法
java8中引入了一个新的操作符 "->",该操作符称为箭头操作符或者Lambda操作符
箭头操作符将Lambda表达式拆分成两部分:
左侧:Lambda的参数列表
右侧:Lambda表达式中所需执行的功能,即Lambda体
1) 语法格式1
参,并且无返回值
() -> System.out.println("hello lambda")
@Test public void test1(){ int num = 0; // jdk7以前必须是final Runnable r = new Runnable() { @Override public void run() { System.out.println("hello,Lambda!!!" + num); } }; r.run(); System.out.println("----------------------------------------"); Runnable r1 = () -> System.out.println("hello lambda!!!"); r1.run(); }
2) 语法格式2
有一个参数,并且无返回值
3) 语法格式3
若左侧只有一个参数,那么左边的 ()可以不写
@Test public void test2(){ Consumer<String> con = (x) -> System.out.println(x); con.accept("后臣特别特别帅@-@"); Consumer<String> con1 = x -> System.out.println(x); con1.accept("后臣特别特别帅@-@"); }
4) 语法格式4
有两个以上的参数,有返回值,并且Lambda 体中有多条语句
Comparator<Integer> comparator = (x,y) -> { System.out.println("函数式接口"); return Integer.compare(x,y); };
5)语法格式5
如果lambda中只有一条语句,那么可以省略{} + return
@Test public void test3(){ Comparator<Integer> comparator = (x,y) -> { System.out.println("函数式接口"); return Integer.compare(x,y); }; System.out.println("--------------------------------------"); Comparator<Integer> comparator1 = (x,y) -> Integer.compare(x,y); }
6) 语法格式6
Lambda表达式的参数列表的的数据类型可以省略不写,因为JVM编译期可以通过上下文推断出数据
类型,即“类型推断” ......
Comparator<Integer> comparator1 =
(Integer x,Integer y) -> Integer.compare(x,y);
3、Lambda 表达式需要”函数式接口"的支持
函数式接口:接口中只有一个抽象方法的接口,称为函数式接口
可以使用 @FunctionalInterface修饰,可以检查是否是函数式接口(修饰的接口只能有一个抽象方法)
4、Lambda的练习
/** * @author houChen * @date 2020/12/25 21:37 * @Description: Lambda表达式 例子 */ public class TestLambda3 { List<Employee> employees = Arrays.asList( new Employee("张三",18,3000), new Employee("李四",45,4000), new Employee("王五",37,3000), new Employee("赵六",18,6000)); /** * @Description: 先按照年龄排序,年龄相同按照name比较 * @param null * @author houChen * @date 2020/12/26 11:42 */ @Test public void test(){ Collections.sort(employees,(e1,e2) -> { if(e1.getAge()==e2.getAge()){ return e1.getName().compareTo(e2.getName()); }else{ return Integer.compare(e1.getAge(),e2.getAge()); } }); for(Employee e:employees){ System.out.println(e); } } /** * @Description: 将字符串转大写 * @param null * @author houChen * @date 2020/12/26 11:56 */ @Test public void test1(){ String upStr = StrHandler("hello,lambda", str -> str.toUpperCase()); System.out.println(upStr); } //用于处理字符串 public String StrHandler(String str,MyFunction mf){ return mf.getValue(str); } // 计算两个Long型数据相加的he @Test public void test2(){ Long result = op(1l, 2l, (x, y) -> x + y); System.out.println(result); } public Long op(Long l1,Long l2,MyFunction2<Long,Long> mf){ return mf.getValue(l1, l2); } } public interface MyFunction { public String getValue(String str); } public interface MyFunction2<T,R> { public R getValue(T t1,T t2); }
5、四大内置核心函数式接口
用途
T
确定类型为T 的对象是否满足某约束,并返回boolean值。包含方法
boolean test(T t)
函数式接口 |
参数类型 |
返回类型 |
|
Consumer<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> 断定型接口 |
boolean |
四大内置函数式接口的demo
package com.atguigu.FuntionInterface4; import com.atguigu.Employee; import org.junit.Test; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Predicate; import java.util.function.Supplier; /** * @author houChen * @date 2020/12/27 19:50 * @Description: * * java8 内置的四大核心函数式接口 * * Consumer<T>:消费型接口 * void accept(T t); * * Supplier<T> : 供给型接口 * T get() * * Function<T,R>:函数型接口 * R apply(T t) * * Predicate<T> : 断言型接口 * boolean test(T t) * */ public class TestLambda { //Consumer: 消费型接口 @Test public void test1(){ happy(35,d -> System.out.println("花费了"+d)); } public void happy(double money, Consumer<Double> con){ con.accept(money); } //Supplier<T> 供给型接口 @Test public void test2(){ List<Integer> numberList = getNumberList(10, () -> (int) (Math.random() * 100)); for(Integer num : numberList){ System.out.println(num); } } //需求:产生一些整数,并放在集合中 public List<Integer> getNumberList(int num, Supplier<Integer> sup){ List<Integer> list = new ArrayList<>(); for(int i = 0; i < num ; i++){ list.add(sup.get()); } return list; } // Function<R,t> 函数型接口 @Test public void test3(){ String result = Strandler(" hello world,i like china!", str -> str.trim()); System.out.println(result); } //需求:用于处理字符串 public String Strandler(String str, Function<String,String> fun){ return fun.apply(str); } //Predicate<T> : 断言型接口 // @Test public void test4(){ List<String> employees = Arrays.asList("hello","houchen","shuchenxi"); List<String> list = filterStr(employees, str -> str.length() >3); for(String s : list){ System.out.println(s); } } //需求:将满足条件的字符串放入集合中 public List<String> filterStr(List<String> list, Predicate<String> pre){ List<String> stringList = new ArrayList<>(); for(String str : list){ if(pre.test(str)){ stringList.add(str); } } return stringList; } }