Python 平铺数据并映射

Python 平铺数据并映射前面介绍了将嵌套元组平铺为简单可迭代对象的算法。当时的目标只是改变数据结构,没有对数据做实质性处理,下面介绍如何将处理函数和平铺操作结合起来。

假设需要把如下文本转换为一维数值序列:

>>> text= """\
...   2   3   5   7  11  13  17  19  23  29
...  31  37  41  43  47  53  59  61  67  71
...  73  79  83  89  97 101 103 107 109 113
... 127 131 137 139 149 151 157 163 167 173
... 179 181 191 193 197 199 211 223 227 229
... """

每行包含10个数据,接下来要把所有行合并为一个数值序列。

通过下面这个由两部分组成的生成器函数实现数据转换:

data = list(
    v
    for line in text.splitlines()
    for v in line.split()
)

首先将整个文本分为多行,遍历每一行。在一行中,再将文本分为许多词组,输出是一个字符串列表,如下所示:

['2', '3', '5', '7', '11', '13', '17', '19', '23', '29', '31', '37',
 '41', '43', '47', '53', '59', '61', '67', '71', '73', '79', '83',
 '89', '97', '101', '103', '107', '109', '113', '127', '131', '137',
 '139', '149', '151', '157', '163', '167', '173', '179', '181', '191',
 '193', '197', '199', '211', '223', '227', '229']

除了改变格式,为了将字符串转换为数值,还需要增加一个转换函数,如下所示:

from numbers import Number
from typing import Callable, Iterator

Num_Conv = Callable[[str], Number]

def numbers_from_rows(
        conversion: Num_Conv, text: str) -> Iterator[Number]:
    return (
        conversion(value)
        for line in text.splitlines()
        for value in line.split()
    )

该函数有个conversion参数,作为转换函数,处理前面平铺算法生成的每个值。

如下所示使用numbers_from_rows()函数:

print(list(numbers_from_rows(float, text)))

这里使用内置函数float()将一段文本转换为了一个浮点数列表。

可以将高阶函数和生成器表达式相结合来改写上面的函数,如下所示:

map(float,
    value
    for line in text.splitlines()
    for value in line.split()
)

这种实现方法有助于我们理解算法的整体结构。采用组块原则,函数的具体实现通过一个有意义的名字进行抽象,然后将其用于新的上下文中。虽然通常使用高阶函数,但某些情况下使用生成器表达式能使算法更简便。

Python教程

Java教程

Web教程

数据库教程

图形图像教程

大数据教程

开发工具教程

计算机教程