📔C2 Lambda介绍
type
status
date
summary
slug
tags
category
icon
password
Chapter2:Passing code with behavior parameterization
This chapter covers:
- Coping with changing requirements
- Behavior parameterization
- Anonymous classes
- Preview of lambda expressions
例子:农夫的请求
第一种方法:选出绿色的苹果
现在有一个农夫,想请你帮助他写一个分出货架上绿色苹果的代码,这对你来说是小菜一碟。
农夫很高兴,于是他又问你:你能帮我挑出红色的苹果吗?
当然没问题!只需要复制上面的
filterApplesByColor()
方法,修改其中的if
语句就好了。然而,这种处理方式在农夫提出更多需求时表现得并不好:如果他还想要分出青绿色、深红色、黄色的苹果呢?难道每一个请求都要重写一次方法吗?
作者提到,我们在编写代码时有一个原则:after writing similar code, try to abstract.
我们该如何对代码进行抽象化处理呢?
第二种方法:将颜色参数化
为了选出不同颜色的苹果,你想到:将
color
作为参数传递给filterApplesByColor()
方法,这样就不用写多个相似的方法了。农夫很开心,于是他又向你提出新的需求:我想选出重量大于150克的苹果。
这个简单,写一个
filterApplesByWeight()
方法不就好了吗!这是一个很好的解决方案,但是必须复制大部分代码,以便遍历清单并在每个苹果上应用过滤条件。如果你想更改遍历方式以提高性能怎么办呢?难道要一个个的对方法进行修改吗?这显然太麻烦了。
第三种方法:使用你能想到的所有属性进行筛选
作者提到,这是一种很丑陋(ugly)的写法:
这种写法可以用于指定的问题,不过眼下的情况是,你需要一种更好的方法来告诉
filterApples
方法苹果的选择标准。于是,行为参数化(behavior parameterization)闪亮登场了。行为参数化
通过一个
ApplePredicate
接口,我们可以对上文提到过的选择标准进行建模(model)。现在,如下图所示,通过编写不同的实现类,你可以满足农夫多样的请求了!
你可以把这些选择标准看作
filter
方法不同的行为。与此同时,你其实也使用到了策略设计模式!有关策略设计模式的内容可以参考:http://en.wikipedia.org/wiki/Strategy_pattern.上述便是行为参数化的含义:告诉方法将多个行为(或策略)作为参数并在内部使用它们来完成不同行为的能力。通过这样做,你现在可以将
filterApples
方法中迭代集合的逻辑与要应用于集合的每个元素的行为分开。更简单的写法:匿名类
现在,你已经会使用接口和实现类来满足不断变化的需求了。但是,声明那些只使用一次的类也是一个繁琐的工作。因此,匿名类(Anonymous classes),作为一种更简洁的写法出现了。
下面的代码展示了如何通过匿名类对过滤方法进行重写。
通过匿名内部类,你可以同时声明和使用方法,看起来比声明多个实现类轻松多了。
不过,匿名内部类也并非最好的选择,因为它有两个缺点:
- 它让代码看起来十分臃肿。
- 有时候使用起来让人困惑。
下面是书中给出的一段程序,你能给出它执行后的结果吗?
答案是5!
因为
this
指向的是Runnable
,而并非MeaningOfThis
类。还有更好的解决方法:Lambda表达式。详情见Java8 In Action C3。
总结
通过阅读这一章,你应该知道:
- 行为参数化是指方法将多个不同的行为作为参数并在内部使用它们来完成不同行为的能力。
- 行为参数化可让你的代码更适应不断变化的需求,并节省将来的工程工作量。
- 传递代码(Passing code)是一种将新行为作为参数提供给方法的方法。在 Java 8 之前,传递代码是一个冗长的过程。匿名类虽然有助于减少为接口声明多个一次性具体类的繁琐,但仍不够简洁。
Prev
关于秋招
Next
C3 Lambda详解
Loading...