Java8-------行为参数化

本文介绍了一种使用Java8进行高效筛选的技术,通过逐步改进代码,实现了对不同苹果属性的灵活筛选,最终达到行为参数化的目的。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本人Java8系列博客全是对< Java8实战 >,这本书的总结,不是代码生产者,只是个勤劳的搬运工.
相比枯燥的概念,本人更愿意通过实际例子说明.

需求1

需求1: 选出绿苹果:
第一个解决方案可能是下面这样的

   //选出绿苹果
    public static List<Apple> filterGreenApples(List<Apple> inventory) {
        List<Apple> result = new ArrayList<Apple>();
        for (Apple apple : inventory) {
            if ("green".equals(apple.getColor())) {
                result.add(apple);
            }
        }
        return result;
    }

需求2

需求2:想要筛选多种颜色:浅绿色、暗红色、黄色等,上述方法就应付不了了。一个良好的原则是在编写类似的代码之后,尝试将其抽象化。可以将颜色当做参数传入.

//改进::把颜色作为参数
    public static List<Apple> filterApplesByColor(List<Apple> inventory, String color) {
        List<Apple> result = new ArrayList<Apple>();
        for (Apple apple : inventory) {
            if (apple.getColor().equals(color)) {
                result.add(apple);
            }
        }
        return result;
    }

需求3

需求3: 要是能区分轻的苹果和重的苹果就太好了。重的苹果一般是重量大于150克

public static List<Apple> filterApplesByWeight(List<Apple> inventory, int weight) {
        List<Apple> result = new ArrayList<Apple>();
        for (Apple apple : inventory) {
            if (apple.getWeight() > weight) {
                result.add(apple);
            }
        }
        return result;
    }

这时我们会发现,这段代码与需求1的代码几乎是一样的,有点儿令人失望,因为它打破了DRY(Don’t Repeat Yourself,不要重复自己)的软件工程原则,接下来引出:行为参数化 解决上述问题 这种做法类似于策略设计模式

代码改进1:

    //抽象化接口
    public interface ApplePredicate {
            boolean test(Apple apple);
    }

    public static List<Apple> filterApples(List<Apple> inventory, ApplePredicate p) {
        List<Apple> result = new ArrayList<Apple>();
        for (Apple apple : inventory) {
            if (p.test(apple)) {
                result.add(apple);
            }
        }
        return result;
    }

    public static void main(String[] args) {
        filterApples(new ArrayList<Apple>(), new ApplePredicate() {
            @Override
            public boolean test(Apple apple) {
                return apple.getWeight() > 150;
            }
        });
    }

*这里值得停下来小小地庆祝一下。这段代码比我们第一次尝试的时候灵活多了,读起来、用起来也更容易!现在你可以创建不同的ApplePredicate对象,并将它们传递给filterApples方法。免费的灵活性!比如,如果农民让你找出所有重量超过150克的红苹果,你只需要创建一个类来实现ApplePredicate就行了。你的代码现在足够灵活,可以应对任何涉及苹果属性的需求变更了.


代码改进2:匿名内部类毕竟啰嗦,使用Lambda 表达式简化

public static void main(String[] args) {
        filterApples(new ArrayList<Apple>(), (Apple apple) -> "red".equals(apple.getColor()));
    }

代码改进3: * 在通往抽象的路上,我们还可以更进一步。目前,filterApples方法还只适用于Apple(如何适应其他水果呢?) 你还可以将List类型抽象化,从而超越你眼前要处理的问题:

public interface ApplePredicate<T> {
        boolean test( T t);
    }

    public static <T> List<T> filterApples(List<T> inventory, ApplePredicate<T> p) {
        List<T> result = new ArrayList<T>();
        for (T t : inventory) {
            if (p.test(t)) {
                result.add(t);
            }
        }
        return result;
    }

    public static void main(String[] args) {
        //使用泛型
        //好了,现在对象可以不只是apple了,对于其他水果也同样适用
        filterApples(new ArrayList<>(), (Apple apple) -> "red".equals(apple.getColor()));
    }

经过一系列改进后代码,相对一开始是不是可以满足不同的客户需求…

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值