• Lambda表达式与函数式接口


    1 Lambda表达式

    Java8 新特性

    1.1 从匿名内部类到Lambda

    匿名内部类的作用:当一个内部类只需为其创建一次对象,且以后也不会再被用到,就可以使用匿名内部类简化代码编写。

    例子:创建线程。

    new Thread(new Runnable() {
        @Override
        public void run() {
    		System.out.println("CLASS");
        }
    }).start();
    

    Lambda表达式:大部分场景下可以取代匿名内部类的新特性。

    创建线程的代码可以简化为

    new Thread(() -> {
        System.out.println("LAMBDA");
    }).start();
    

    此外,Lambda表达式还可以结合forEach用于容器的遍历。只需一行即可完成遍历。

    list.forEach(x -> System.out.println(x));
    

    1.2 Lambda语法

    完整的格式

    (TYPE parameter, TYPE parameter) -> { code }
    

    做减法,可以分情况省略部分。

    "()" 当parameter只有一个时,可以省略,例如list.forEach(x -> System.out.println(x));

    "{}" 当code只有一行时,可以省略,例子同上。

    "TYPE" 参数类型总是可以省略,编译器会自动识别。

    1.3 使用Lambda表达式的限制

    Lambda表达式只能实现函数式接口。

    2 函数式接口

    函数式接口(Functional Interface)就是一个有且仅有一个抽象方法,但是可以有多个非抽象方法的接口。

    2.1 @FunctionalInterface

    一个让编译器强制检查接口是否为函数式的注解。

    2.2 函数式接口的类型

    Java在1.8之前就有一些函数式接口:Runnable,Callable,Comparator,FileFilter等等。

    Java1.8又新增了一批函数式接口,放在java.util.function包下(图未截完整)

    2.3 从函数式接口到Lambda

    2.3.1 Consumer

    Consumer:位于java.util.function包下,接收一个泛型的参数T,然后调用accept,对这个参数进行操作(accept为抽象方法,具体做什么操作由实现决定),没有返回值。

    @FunctionalInterface
    public interface Consumer<T> {
       	void accept(T t);
        //非抽象方法略
    }
    

    上面提到的forEach就接收了一个Consumer泛型接口

    default void forEach(Consumer<? super T> action) {
        Objects.requireNonNull(action);
        for (T t : this) {
            action.accept(t);
        }
    }
    

    回到forEach配合Lambda进行遍历

    list.forEach(x -> System.out.println(x));
    

    Lambda表达式实现了Consumer接口,accept方法被重写为打印接收的参数x,在forEach方法内部通过for循环完成遍历。

    2.3.2 Predicate

    Predicate:位于java.util.function包下,接收一个泛型参数T,测试其是否符合test方法中的规则(test方法为抽象方法,具体规则由实现决定),返回一个boolean值。

    @FunctionalInterface
    public interface Predicate<T> {
        boolean test(T t);
        //非抽象方法略
    }
    

    removeIf:Collection中方法,用于条件删除容器中的元素,接收一个Predicate泛型接口。

    default boolean removeIf(Predicate<? super E> filter) {
        Objects.requireNonNull(filter);
        boolean removed = false;
        final Iterator<E> each = iterator();
        while (each.hasNext()) {
            if (filter.test(each.next())) {
                each.remove();
                removed = true;
            }
        }
        return removed;
    }
    

    删除list中小于3的元素

    list.removeIf(x -> x < 3);
    
  • 相关阅读:
    JAVA高级篇(二、JVM内存模型、内存管理之第二篇)
    JAVA高级篇(三、JVM编译机制、类加载机制)
    spring batch (二) 元数据表
    spring batch (一) 常见的基本的概念介绍
    ORACLE——EXTRACT() 截取日期时间的函数使用
    ORACLE——NVL()、NVL2() 函数的用法
    ORACLE删除分区
    ORACLE中关于使用between在MyBatis中取不同的区间值和取反
    ORACLE——count() 统计函数的使用
    Oracle——trunc()函数的使用
  • 原文地址:https://www.cnblogs.com/CofJus/p/14459622.html
Copyright © 2020-2023  润新知