函数式编程,Lambda表达式

函数式接口:有且只有一个抽象方法的接口。用来表示Lambda表达式的类型。

函数作为一等公民

  • 可以被定义
  • 可以作为参数
  • 可以作为返回值

Java8新增了注解@FunctionalInterface,用于标识一个接口为函数式接口。

接口新特性

  • 接口支持默认方法

支持default关键字

 1 @FunctionalInterface
 2 public interface Consumer<T> {
 3 
 4     void accept(T t);
 5 
 6     default Consumer<T> andThen(Consumer<? super T> after) {
 7         Objects.requireNonNull(after);
 8         return (T t) -> { accept(t); after.accept(t); };
 9     }
10 }
  • 接口支持静态方法

 支持static修饰方法体

1 @FunctionalInterface
2 public interface UnaryOperator<T> extends Function<T, T> {
3 
4     static <T> UnaryOperator<T> identity() {
5         return t -> t;
6     }
7 }

 

Lambda表达式语法:

  • 参数
  • 箭头符号
  • 主体

 

Lambda表达式形式

Runnable noArguments = () -> System.out.println("Hello World"); 无参数,无返回值。
ActionListener oneArgument = event -> System.out.println("button clicked");

有参数,无返回值。只有一个参数可以省略参数括号

Runnable multiStatement = () -> {

  System.out.println("Hello");

  System.out.println(" World");

}

无参数,无返回值。有多个表达式语句,用大括号括起来。

BinaryOperator<Long> add = (x, y) -> x +y;

多个参数,有返回值。参数无显式类型。

BinaryOperator<Long> addExplicit = (Long x, Long y) -> x + y;

参数显式声明。

 

Java8新增函数式接口

接口 参数 返回类型
Predicate<T> T boolean
Consumer<T> T void
Function<T, R> T R
Supplier<T> None T
UnaryOperator<T> T T
BinaryOperator<T> (T, T) T

其他内置函数式接口

接口 参数 返回类型
Runnable None void
Callable<V> None V
Comparator<T> T int
FileFilter File boolean
Comparable<T> T int

 数据和行为分离

复合Lambda表达式

  • 比较器复合

逆序

1   Comparator.comparing(String::length).reversed();

比较器链

1     Comparator.comparing(String::length).thenComparing(Comparator.naturalOrder());
  • 谓词复合

包含三个方法:negate、and、or。

1     Predicate<Person> isMale = Person::isMale;
2 
3     Predicate<Person> notMale = isMale.negate();
4     Predicate<Person> isMaleAndIsChildren = isMale.and(Person::isChildren);
5     Predicate<Person> isMaleOrIsChildren = isMale.or(Person::isChildren);
  • 函数复合

andThen、compose

 1     UnaryOperator<Integer> u1 = x -> x + 1;
 2     UnaryOperator<Integer> u2 = x -> x * 2;
 3     
 4     // 先执行u1,再执行u2
 5     Function<Integer, Integer> f1 = u1.andThen(u2);
 6     // 先执行u2,再执行u1
 7     Function<Integer, Integer> f2 = u1.compose(u2);
 8      9     f1.apply(1); // (1 + 1) * 2 = 4
10     11     f2.apply(1); // (1 * 2) + 1 = 3

 

上一篇:千万数据快速模拟插入


下一篇:webpack 手写的loader引入报错 Module not found: Error: path argument is not a string