定义
所谓的函数式接口,当然首先是一个接口,然后就是在这个接口里面只能有一个抽象方法
函数式接口实例创建的三种方法
- Lambda
- 方法引用
- 构造方法引用
简单示例(Lambda)
@FunctionalInterface
public interface GreetingInterface {
void hello();
}
public class App {
public static void main( String[] args ) {
GreetingInterface greeting = () -> {
System.out.println("Hello World!");
};
greeting.hello();
}
}
- 与传统的实现接口不同,这里使用
Lambda
表达式实现了接口中的方法,不用再写一个.java
文件,这样写很明显的缺点就是复用性不高,这就是函数式编程,在适合情况下使用 - 函数式接口中只能有一个抽象方法,简单认为就是一个接口就是一个方法
- Java8提供了
@FunctionalInterface
标识函数式接口,当编写的函数式接口不符合定义时会报错,和@Override
一样,加不加不会影响函数式接口,加上后编译器会主动检查接口是否仅含一个抽象方法
方法引用
public class App {
public static void main(String[] args) {
GreetingInterface greeting = App::sayHello;
greeting.hello();
}
public static void sayHello() {
System.out.println("Hello World!");
}
}
方法引用
也是Lambda
表达式,只是一种简洁的写法,可以实现相同的结果- 引用现有的方法,可以减少代码量,可读性更强
构造方法引用
@FunctionalInterface
public interface GreetingInterface {
MyClass hello(String name);
}
public class MyClass {
private String name;
public MyClass() {
this.name = "Hello World!";
}
public MyClass(String name) {
this.name = name;
}
public void sayHello() {
System.out.println(this.name);
}
}
public class App {
public static void main(String[] args) {
GreetingInterface greeting = MyClass::new;
// 会调用 MyClass(String name)构造方法
MyClass myClass = greeting.hello("Hello World");
myClass.sayHello();
}
}
接口中的其他方法
以下的方法都是合法的:静态方法和默认方法不是抽象方法,所有的类都会继承java.lang.Object
,所以可以包含其中的方法,符合函数式接口的定义
@FunctionalInterface
public interface GreetingInterface {
// 抽象方法
MyClass hello(String name);
// 静态方法
static void hello2() {
System.out.println("static method in functional interface");
}
// 默认方法
default void hello3() {
System.out.println("default method in functional interface");
}
// java.lang.Object的public方法
@Override
boolean equals(Object object);
// java.lang.Object的public方法
@Override
String toString();
}
静态方法和默认方法的使用
public class App {
public static void main(String[] args) {
// 调用静态方法
GreetingInterface.hello2(); // static method in functional interface
// 调用用默认方法
GreetingInterface greeting = new GreetingInterface() {
@Override
public MyClass hello(String name) {
return null;
}
};
greeting.hello3(); // default method in functional interface
}
}