
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人
2.1.7 列表推导式
如前所述,在Python中我们可以使用列表推导式过滤和映射列表。在处理列表时,这种形式通常比filter和map函数更好,因为它的语法更简洁和易读。
列表推导式映射列表的语法结构如下:

它分为两个部分:
❍for<item>in<list>是一个for循环,负责迭代<list>中的元素;
❍<expression>是一个映射表达式,负责将<item>映射到其他东西上。
让我们重复之前做过的练习,将一个名称列表映射到每个名称的长度列表,这次使用列表推导式:

或许你已经明白,为什么Python程序员倾向于使用列表推导式而非map函数;上面的例子读起来就像日常英语:“name列表中(每个)名称的名称长度。”在本例中,for name in names遍历原始列表中的名称,然后将每个名称的长度(len(name))作为结果输出。
使用列表推导式过滤列表,可以在推导式的末尾添加一个if子句:

例如,如果我们想过滤一个名称列表,只保留以A开头的名称,列表推导式可以这么写:

本例中有两点需要注意:映射表达式是name自身(恒等映射,映射后的对象不变),过滤操作使用了字符串的startswith方法。只有当字符串以给定的参数作为前缀时,此方法才会返回True。
我们可以在同一个列表推导式中进行过滤和映射操作。例如,假设我们想过滤名称列表中超过5个字母的名称,然后构造一个新的列表,其元素是原名称及其长度组成的元组。我们可以很容易地做到这一点:

为了便于比较,让我们看看如果使用filter和map函数,会是什么样子:

如你所见,结果相同,但列表推导式的版本更简单易读。越容易阅读的东西也越容易维护,因此列表推导式将是我们过滤和映射列表的首选方式。
现在让我们将注意力转向第二个范式:面向对象编程。