为什么使用reduce与非关联运算符被认为是坏风格?

时间:2017-07-30 19:19:33

标签: python reduce associativity

正如Guido在The fate of reduce() in Python 3000帖子中所说:

  

所以现在减少()。这实际上是我一直非常讨厌的那个,因为除了几个涉及+或*的例子之外,几乎每当我看到一个带有非平凡函数参数的reduce()调用时,我都需要抓住笔和在理解reduce()之前应该做什么之前,用纸来说明实际上被输入到该函数中的内容。所以在我看来,reduce()的适用性几乎局限于关联​​运算符,在所有其他情况下,最好明确地写出累积循环。

我对声明感到困惑:

  

reduce()的适用性几乎仅限于关联运算符

在python中仅仅进行了一次简单的操作(从左到右)?如果与sets或dict键一起使用,我得到的顺序可能是非确定性的 - 这是唯一的原因吗?

以下是非关联操作的一个很好的reduce用法示例:

def pass_thru(prev, next_func):
    return next_func(prev)

def flow(seed, *funcs):
    return reduce(pass_thru, funcs, seed)

flow('HELLO',
     str.lower,
     str.capitalize,
     str.swapcase)
#returns 'hELLO'

我担心的是,我是否应该担心对未来的多线程实现进行无保证的一致性,或者只注意像set和dict这样的非确定性迭代。

1 个答案:

答案 0 :(得分:1)

虽然我不得不说我同意你的意见,但我真的很喜欢你提出的flow例子,

我可以看到Guido声称减少的一些优点并不像直接循环那样明确。如果你不习惯FP的高阶函数,那可能会让人感到困惑。

我认为mapfilterzip这样的高阶函数非常有用,它们本质上是声明性的,并没有定义显式实现。

您可以使用spark的{​​{1}},map的{​​{1}}或内置multiprocessing.Pool,返回值应为相同。

但是,当谈到map时,实现本质上是串行的。事实上,你没有使用直接循环获得任何抽象。

因此,我可以看到map如何与禅宗的Python发生冲突:

  

应该有一个 - 最好只有一个 - 显而易见的方法。