赞
踩
1、需要自定义简单的代码块,不想写单独的方法调用。
2、日志输入不输入实现类信息,通过函数接口封装父类可以隐藏子类的实现过程,不会暴露把具体实现暴露在日志系统中。
3、可以作物业务前后的补充,先定义实现然后根据需求回调业务。
当代码中出现"->"、"::"第一反应就是他用lambda表达式。
A a=b->b++;
b就是我们出入参数,可以使用(b)、(int b)、b。
b++ 就是我们业务代码块,自定义的实现方式,相当于一个方法的内容实现。可以是{b++;};、b++。
A a=B::get;
get是B类中的一个方法。
B可以是类也可以是对象。
这里才代码块的真正调用。
a.put©;
a是类A的别名,可能有疑问不用管他就这么定义。
put是A类的唯一抽象方法。
c标识我们出入代码的参数,就像方法的传参。
进行函数式编程我们必须要先定义函数式接口,函数式接口使用 @FunctionalInterface 注解,提供一个唯一的抽象方法。
//之前函数式编程就已经出现的方式,是不是很熟悉,只不过我们之前用的比较少,在线程和异步的时候使用。
Runnable runnable = new Runnable(){
@Override
public void run() {
System.out.println("我最帅");
}
};
runnable.run();
lambda 表达式格式
函数接口 名称= (传参){接收参数,业务逻辑};
Runnable r1 = ()->{System.out.println("你第二帅");};
Runnable r2 = ()->System.out.println("你第二帅1");
//调用接口函数
r1.run();
r2.run();
我使用的例子是有参数有返回值的函数接口方法
1、如果有多个参数,自己会匹配参数类型,不用定义参数类型
2、(参数){使用参数} 在{}中使用传递的参数进行业务逻辑的处理
3、如果没有定义返回值类型,就算我们在{return} 也是接收不到返回的数据。
LambdaInterface la = new LambdaInterface(){ @Override public String get(Integer i) { return "自定义函数返回"; } }; System.out.println(la.get(1)); LambdaInterface la1 = (i)->{return i+"返回数据" ;}; LambdaInterface la2 = (i)->{return "单独返回数据" ;}; LambdaInterface la3 = (i)->{ i=i*100; //传入的参数做业务处理 return i+"业务处理,返回数据" ; }; LambdaInterface la4 = (i)->"固定返回数据"; LambdaInterface la5 = (Integer i)->{return i+"带传参的数据类型,返回数据" ;}; LambdaInterface la6 = i->{return i+"不用()定义传参,返回数据" ;}; System.out.println(la1.get(100));
LambdaInterface自定义函数接口
@FunctionalInterface
public interface LambdaInterface {
public String get(Integer i);
}
方法引用 比(){} 更简洁的方式
类的实例或者类名::方法名;
LambdaInterface laa = a->LambdaA.get(a);
LambdaInterface laa1 = LambdaA::get;
System.out.println(laa.get(1));
System.out.println(laa1.get(1));
LambdaA类的测试方法
public class LambdaA { public static String get(String a){ return "LambdaA 的get"; }; public static String get(Integer integer) { return "LambdaA 的get integer"+integer; }; public static String get1() { return "LambdaA 的无参get"; }; public static void in(Integer i) { i++; }; public static void inDouble(String s, Integer integer) { }; public static Integer inGet(String s) { return 1; }; public static String inUGet(String s) { return "UnaryOperator"; } public static Integer inDoubleget(String s, String s1) { return 1; } public static String inDoubleOGet(String s, String s1) { return ""; } public String get() { return ""; } public static String getT() { return ""; } public LambdaA() { } public LambdaA(String a){ } }
java 提供几个标准函数接口 就不用我们自己定义函数接口了
Supplier 代表一个输出
Consumer 代表一个输入
BiConsumer 代表两个输入
Function 代表一个输入,一个输出(一般输入和输出是不同类型的)
UnaryOperator 代表一个输入,一个输出(输入和输出是相同类型的)
BiFunction 代表两个输入,一个输出(一般输入和输出是不同类型的)
BinaryOperator 代表两个输入,一个输出(输入和输出是相同类型的)
输入的参数需要指定泛型,否则出输入的参数应该Object。
Supplier s1 =LambdaA::get1; System.out.println(s1.get()); Consumer<Integer> c1 = LambdaA::in; int i = 0; c1.accept(i); System.out.println(i); BiConsumer<String,Integer> b1 = LambdaA::inDouble; b1.accept("",1); Function<String,Integer> f1 = LambdaA::inGet ; f1.apply("1"); UnaryOperator<String> u1 = LambdaA::inUGet; u1.apply("1"); BiFunction<String,String,Integer> bf1 = LambdaA::inDoubleget; bf1.apply("1","2"); BinaryOperator<String> bo1 = LambdaA::inDoubleOGet; bo1.apply("2","1");
静态方法引用 类名::staticMethod (args) -> 类名.staticMethod(args)
实例方法引用 inst::instMethod (args) -> inst.instMethod(args)
对象方法引用 类名::instMethod (inst,args) ->类名.instMethod(args)
构造方法引用 类名::new (args) -> new 类名(args)
//静态方法引用
Supplier s2 =LambdaA::get1;
//实例方法引用
LambdaA lA = new LambdaA();
Supplier<String> s3 =lA::get;
//对象方法引用 自动调用无参构造方法生成对象
Supplier<String> s4 =LambdaA::getT;
//构造方法引用
Consumer<String> s5 = LambdaA::new;
s5.accept("");
代码地址
https://gitee.com/zhang798/javaDemo.git
分支 java_lambda
git clone https://gitee.com/zhang798/javaDemo.git -b java_lambda
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。