将嵌套循环转换为 map/reduce/filter

Convert nested loop to map/reduce/filter

作为学习 python map/reduce/filter 方法的一部分,我有一个练习 - 仅使用 map/reduce/filter 将函数转换为一行代码。 这是需要转换的函数:

def func5(n):
    l = []
    for i in range(n):
        j = 0
        while j < i:
            if j % 2 == 0:
                l.append(j + 5)
            elif j % 3 == 0:
                l.append(j // 2)
            elif j % 5 == 2:
                l.append(j)
            j += 1
    return l

所以我认为我已经正确地完成了 if-else,但我不知道在 lambda 命令中创建嵌套循环的语法是什么(我们不应该使用 for 循环)。 到目前为止我的代码:

l = list(map(lambda x: x+5 if x % 2 ==0 else x//2 if x % 3 ==0 else x if x % 5 ==2 ,_______))

All-in 根据需要在一行中...... reduce 连接列表(默认情况下仅在 functools 模块中可用,不再是 build-in) , filter 消除内联条件的副作用(见我的评论)。

import functools as fc
n = 10
a = fc.reduce(lambda i, j: i+j, map(lambda i: list(filter(None, map(lambda j: j+5 if j%2==0 else (j//2 if j%3==0 else (j if j%5==2 else None)), range(i)))), range(n)))

a = list(a)
print(a)
print(a == func5(n))

输出

[5, 5, 5, 7, 5, 7, 1, 5, 7, 1, 9, 5, 7, 1, 9, 5, 7, 1, 9, 11, 5, 7, 1, 9, 11, 7, 5, 7, 1, 9, 11, 7, 13]
True

在列表理解形式中:

[
    x
    for i in range(n)
    for j in range(i)
    for x in (
        [j + 5]
        if j % 2 == 0
        else [j // 2]
        if j % 3 == 0
        else [j]
        if j % 5 == 2
        else []
    )
]

...可以转换为两个reduce

reduce(
    lambda xs, i: xs
    + reduce(
        lambda ys, j: ys
        + (
            [j + 5]
            if j % 2 == 0
            else [j // 2]
            if j % 3 == 0
            else [j]
            if j % 5 == 2
            else []
        ),
        range(i),
        [],
    ),
    range(n),
    [],
)