Lambda表达式
-
jdk1.8的一个新特性
-
属于一种语法糖
-
主要作用体现在两点
-
对匿名内部类语法简化
-
函数式编程思想锻炼
-
1 匿名内部类的优化
1.1 lambda基本应用
-
lambda优化匿名内部类是有前提条件
-
匿名内部类必须是基于接口的
-
要求接口中只能有1个抽象方法,称之为函数式接口
-
-
lambda如何优化符合函数式接口条件的匿名内部类
interface C{
void t1();
}
C c1 = new C(){
public void t1(){
System.out.println("--------------");
}
}
1.2 lambda语法细节
-
参数列表中可以省略参数类型,也可以保留参数类型
interface A{
void t1(int num1 ,int num2) ;
}
A a1 = (int num1, int num2)->{}
A a2 = (num1,num2) -> {}
参数列表中只有一个参数,可以省略()
interface A{
void t1(int num) ;
}
A a1 = (num)->{}
A a2 = num->{}
-
参数列表中没有参数时,必须保留()
interface A{
void t1();
}
A a = ()->{};
如果方法体中只有一行代码,可以省略{}
interface A{
void t1();
}
A a1 = ()->{System.out.println("A");};
A a2 = ()->System.out.println("A");
如果方法需要返回值,但方法体中只有一行代码,可以省略{}和return关键字
interface A{
int t1();
}
A a1 = ()->{return 100 ;} ;
A a2 = ()-> 100 ;
如果方法体中有多行代码, {}和return关键字都不能省略
interface A{
int t1();
}
A a1 = ()->{
int num = 10 ;
return nun ;
}
1.3 lambda方法引用
-
lambda的方法体中只有一行代码,而且这行代码是调用了另一个方法
-
调用的方法与当前lambda表示的方法有相同的数据处理结构
-
如果给lambda方法传递了n个参数
-
lambda就会原封不动的将这n参数传递给它调用的那个方法
-
如果lambda方法有返回类型。 其调用方法的返回值,lambda会原封不动的返回给调用者
-
interface A{
void t(int num) ;
}
A a1 = new A(){
public void t(int num){
System.out.println(num) ;
}
}
A a2 = num->System.out.println(num) ;
A a3 = System.out::println ;
对象方法引用
在lambda中引用的是一个对象的方法
class A{
public void sum(int num1 , int num2){
System.out.println(num1 + num2);
}
}
interface B{
void t(int n1, int n2) ;
}
A a = new A();
B b1 = (n1,n2)->a.sum(n1,n2);
B b2 = a::sum ;
interface C{
double t(int n1,int n2) ;
}
class A{
public double sum(int num1,int num2){
return num1 + num2 ;
}
}
class B extends A{
public double sum(int num1,int num2){
return (num1 + num2) * 0.9 ;
}
public void test(){
//当lambda生效的时候,一定产生了当前的B对象
C c1 = (n1,n2)->this.sum(n1,n2);
C c2 = this::sum ;
C c3 = (n1,n2)->super.sum(n1,n2);
C c4 = super::sum ;
double r = c2.t(10,20);
System.out.println(r);
}
}
B b = new B();
b.test();
类方法引用
在lambda中引用的是一个类的方法
class A{
public static int sum(int num1,int num2) {
return num1 + num2 ;
}
}
interface B{
int t(int n1, int n2) ;
}
B b1 = (n1,n2)->{return A.sum(n1,n2);};
B b2 = A::sum ;
int r = b1.t(10,20)
构造方法引用
在lambda中引用的是一个构造方法
class Car{
int cno ;
String cnanme ;
String color ;
public Car(int cno , String cname , String color){
...
}
}
interface A{
Car create(int cno , String cname , String color);
}
A a1 = new A(){
public Car create(int cno , String cname , String color){
return new Car(cno,cname,color);
}
};
A a2 = (cno,cname,color)->new Car(cno,cname,color) ;
A a3 = Car::new ;
2 函数式编程
-
函数式编程,属于一种面向过程的设计思想
-
lambda表达式称为 匿名函数。
-
在使用函数式编程时,考虑的不再是程序的结构,而是程序需要执行的功能。
-
也就是一切都基于功能或基于过程进行分析
-
jdk将我们平时编程中的所有的具体的功能情况,总结成了4种通用情况
-
并使用4个接口来表示
-
Predicate 表示所有的断言情况(判断)
提供了一个
boolean test(参数)
方法
-
//根据业务功能分析,需要一个判断处理
//1. 判断一个数字是否是偶数
//2. 判断一个对象登录是否成功,判断用户名密码是否正确
Predicate<Integer> p1 = num->num%2==0 ;
Predicate<User> p2 = user->user.uname.equals("dmc") && user.upass.equals("123");
2.Consumer 表示所有消费情况,传递参数,处理参数,没有返回值
提供了一个 void accept(参数)
方法
Consumer<String> c1 = str-> System.out.println(str) ;
c1.accept("buka");
3.Supplier 表示所有生产情况,没有参数,有返回值 提供了一个 T get()
方法 , 多用于对象的构建
Supplier<Integer> s1 = ()->10 ;
Supplier<Integer> s2 = ()->(int)Math.random()*10 ;
Supplier<Integer> s3 = ()-> Calendar.getInstance().get(Calendar.MINUTE) ;
4.Function 表示所有功能情况,有参数,有返回值
提供了一个 T apply(参数)
方法
Function<String,Integer> f1 = str -> Integer.parseInt(str) ;
Function<String,Integer> f2 = str -> str.length() ;
Integer num = f1.apply("123");
System.out.println(num);