Lambda表达式/函数编程
前提:要求接口中有且只有一个抽象方法
- 函数接口:这个接口有且只有一个抽象方法,使用jdk8新增@FunctionalInterface注解,只能用于接口声明,作用:检测接口中是否只有一个抽象方法
- 语法:(参数名列表,不带类型) -> {实现体(单行语句)} ;
eg:单行语句:无参数 ()-> 单行语句(省略{ })
如果方法没有返回值:
- 实现体有且只有一条命令(语句){ }可以省略
IMessage message = () -> System.out.println("Hello World");
- 多行语句:(参数) -> { 多行语句 }
IMessage message = () -> {
System.out.println("Hello World");
System.out.println("Hello World111");
System.out.println("Hello World11111");
} ;
如果方法有返回值:
- 且现在你的方法体里只有一行进行数据的返回,那么直接使用语句即可,可以不使用return。
interface IMath{
int test(int a,int b);
}
public class Test{
public static void main(String[] args){
IMath msg = (p1,p2) -> p1+p2 ;
//可以随便写,e1,e2也可以
System.out.println(10,20);
}
}
- 方法体有多行代码,此时return不能省略:注意当有{ }时,’}‘后面要有’;’。
interface IMath{
int test(int a,int b);
}
public class Test{
public static void main(String[] args){
IMath msg = (p1,p2) -> {
r1 = r1 + 10;
r2 = r2 + 10;
return r1 + r2;
};
System.out.println(10,20);
}
}
- Lambda表达式中参数名和变量名不要重名,在Lambda表达式(实现体)中使用外部变量隐式被final修饰(不能改了)
方法引用
定义:返回值 方法名(参数列表)
使用:方法名(参数值列表)
函数:y = f(x)
方法引用:面向对象中的方法 = 函数(函数接口 类 一个方法)
jdk1.8新特性 面向函数编程 “::”
实际上引用的本质就是别名
常与lambda表达式连用
引用的方法的具体实现
而方法引用的类型有四种形式:
- 引用某个类的静态方法:类名称::static 方法名称 ;
@FunctionalInterfaceinterface
ISubject<P,R>{
R switchPara(P p);
}
public class Test{
public static void main(String[] args) {
ISubject<Integer,String> stringISubject =
String ::valueOf;
//等同于使用String.valueOf(10);
System.out.println(stringISubject.switchPara(10));
}
}
- 引用某个对象的普通方法:实例化对象 :: 普通方法 ;
interface ISubject<R>{
R switchPara();
}
public class Test{
public static void main(String[] args) {
ISubject<String> subject =
"hello"::toUpperCase;
//等同于使用"hello".toUpperCase;
System.out.println(subject.switchPara());
}
}
- 引用某个特定类的普通方法: 类名称 :: 普通方法(成员方法) ;
interface ISubject<R,P>{
R switchPara(P p1,P p2);
}
public class Test{
public static void main(String[] args) {
ISubject<Integer,String> iSubject =
String :: compareTo;
//比较字符串大小
//等同于new String.compareTo("刘","杨");
System.out.println(iSubject.switchPara("刘","杨"));
}
}
- 引用某个类的构造方法: 类名称 :: new 。
interface ISubject<R,PI,PS>{
R createPerson(PI pi,PS ps);
}
class Person{
private Integer age;
private String name;
public Person(Integer age,String name){
this.age = age;
this.name = name;
}
public String toString(){
return "Person{" + "age="
+ age + "name="+ name +'\'' +"}";
}
}
public class Test{
public static void main(String[] args) {
ISubject<Person,Integer,String> subject =
Person :: new;
//等同于new Person(18,"jiujiu");
Person per = subject.createPerson(18,"jiujiu");
System.out.println(per);
}
}
注意:方法引用一般结合函数式编程使用—方法引用让面向对象和面向函数结合
内建函数式接口:
java.util.function实际上函数分为
功能型函数式接口:public interface Function<T, R> R apply(T t);
供给型函数式接口: public interface Supplier T get();
消费型函数式接口:public interface Consumer void accept(T t);
断言型接口:public interface Predicate boolean test(T t);