Java8--通过行为参数化引出Lambda表达式

前言

本文通过一系列典型应用的需求,引出Lambda。实际体验Lambda的优势

需求1:按照颜色筛选苹果

package com.example.java.part01;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

/**
 * @Author sherry
 * @Description
 * @Date Create in 2019-04-21
 * @Modified By:
 */

public class MainPart01 {
    public static void main(String[] args) {
        List<Apple> apples = createApples();

        System.out.println(apples);

        List<Apple> greenApples = filterApplesByColor(apples, "绿");

        System.out.println(greenApples);
    }

    /**
     * 按照颜色筛选苹果
     * @param apples
     * @param color
     * @return
     */
    private static List<Apple> filterApplesByColor(List<Apple> apples, String color) {
        List<Apple> list = new ArrayList<>();
        for (Apple apple : apples) {
            if (Objects.equals(color, apple.getColor())) {
                list.add(apple);
            }
        }
        return list;
    }

    /**
     * 初始化一堆苹果
     *
     * @return
     */
    private static List<Apple> createApples() {
        List<Apple> list = new ArrayList<>();
        for (int i = 0; i < 30; i++) {
            Apple apple = Apple.builder()
                    .color(i % 2 == 0 ? "红" : "绿")
                    .weight(i)
                    .build();
            list.add(apple);
        }
        return list;
    }
}

需求2:按照质量筛选苹果

    /**
     * 按照质量筛选苹果
     * @param apples
     * @param weight
     * @return
     */
    private static List<Apple> filterApplesByWeight(List<Apple> apples, int weight) {
        List<Apple> list = new ArrayList<>();
        for (Apple apple : apples) {
            if (weight > apple.getWeight()) {
                list.add(apple);
            }
        }
        return list;
    }

分析1:抽象判断方法

我们发现,按照上面的方式,每一种属性的筛选,都需要编写一个筛选方法

我们可以把筛选这个动作作为参数传递给filter方法,这样,每次根据判断内容的不同,传递不同的筛选方法对象即可

优化

    public static void main(String[] args) {
        List<Apple> apples = createApples();

        System.out.println(apples);
        List<Apple> apples1 = filterApples(apples,new AppleColorPredicate("绿"));
        System.out.println(apples1);
    }

    /**
     * 苹果筛选
     * @param apples
     * @param applePredicate
     * @return
     */
    private static List<Apple> filterApples(List<Apple> apples, ApplePredicate applePredicate) {
        List<Apple> list = new ArrayList<>();
        for (Apple apple:apples){
            if (applePredicate.test(apple)){
                list.add(apple);
            }
        }
        return list;
    }
  • 接口
public interface ApplePredicate {

    /**
     * 判断指定的苹果是否满足需求
     * @param apple
     * @return
     */
    boolean test(Apple apple);
}

然后编写AppleColorPredicateAppleWeightPredicate,实现ApplePredicate接口,分别做到按照颜色和质量进行苹果筛选功能

分析2:匿名函数

在分析1中,我们已经对代码进行了优化,但是还不够简洁。

分析1之后,我们其实是把苹果的判断逻辑,封装到了接口实现类中。

这个在有限个判断属性的时候还行,如果属性多,再加上多个属性的组合判断,那么这种实现类就会非常多。

这个时候,我们就想到了匿名函数,如对于颜色的筛选,可以改写为

        List<Apple> apples1 = filterApples(apples, new ApplePredicate() {
            @Override
            public boolean test(Apple apple) {
                return "绿".equals(apple.getColor());
            }
        });

如果使用Lambda表达式,就只需要一行代码

List<Apple> apples1 = filterApples(apples, apple -> "绿".equals(apple.getColor()));

分析3:参数类型化

现在,我们的ApplePredicate只能筛选苹果,我们可以通过参数类型化,可以实现对所有类型的元素进行判断

public interface Predicate<T> {

    /**
     * 判断指定的对象是否满足需求
     * @param t
     * @return
     */
    boolean test(T t);
}

至此,一个比较优良的代码就已经初见雏形了。

满足了代码的简洁性,逻辑的清晰性,以及满足后续迭代变更的便捷

发布了103 篇原创文章 · 获赞 12 · 访问量 4万+

猜你喜欢

转载自blog.csdn.net/m0_37208669/article/details/89441189