mapped array python list reduce map-function

array - reduce python 3



python: ¿se puede traducir en listas de comprensión como map, lambda y filter? (4)

Cuando programo en python, ahora evito map , lambda y filter utilizando las comprensiones de listas porque es más fácil de leer y más rápido de ejecutar. Pero, ¿se puede reemplazar también la reduce ?

Por ejemplo, un objeto tiene un operador union() que funciona en otro objeto, a1.union(a2) , y da un tercer objeto del mismo tipo.

Tengo una lista de objetos:

L = [a1, a2, a3, ...]

Cómo tener la unión () de todos estos objetos con listas de comprensión, el equivalente de:

result = reduce(lambda a, b :a.union(b), L[1:], L[0])


Como la comprensión de una lista genera otra lista, no puede usarla para generar un solo valor. No son para eso. (Bueno ... hay un truco desagradable que usa un detalle de implementación filtrado en versiones antiguas de python que puede hacerlo. Ni siquiera voy a copiar el código de ejemplo aquí. No hagas esto).

Si estás preocupado por los aspectos estilísticos de reduce() y su estilo, no lo estés. Nombra tus reducciones y estarás bien. Así que mientras

all_union = reduce(lambda a, b: a.union(b), L[1:], L[0])

no es genial, esto

def full_union(input): """ Compute the union of a list of sets """ return reduce(lambda a, b: a.union(b), input[1:], input[0]) result = full_union(L)

es bastante claro

Si te preocupa la velocidad, revisa los paquetes toolz y cytoolz , que son ''rápidos'' y ''increíblemente rápidos'', respectivamente. En grandes conjuntos de datos, a menudo le permitirán evitar procesar sus datos más de una vez o cargar todo el conjunto en la memoria a la vez, en contraste con las listas de comprensión.


No es ningún secreto que reducir no está entre las funciones favorecidas de los pitonistas.

En general, reduce es un pliegue a la izquierda en una lista.

Conceptualmente es fácil escribir un pliegue en Python que se pliegue a la izquierda o a la derecha en un iterable:

def fold(func, iterable, initial=None, reverse=False): x=initial if reverse: iterable=reversed(iterable) for e in iterable: x=func(x,e) if x is not None else e return x

Sin un truco atroz, esto no se puede replicar en una comprensión porque no hay una función de tipo acumulador en una comprensión.

Simplemente use reducir, o escriba uno que tenga más sentido para usted.


Realmente no. Las comprensiones de listas son más similares al map y, posiblemente, al filter .


Un uso común de reducir es aplanar una lista de listas. Puede utilizar una lista de comprensión en su lugar.

L = [[1, 2, 3], [2, 3, 4], [3, 4, 5]]

con reducir

from functools import reduce # python 3 flattened = reduce(lambda x, y: x + y, L) print(flattened) [1, 2, 3, 2, 3, 4, 3, 4, 5]

con lista comp

flattened = [item for sublist in L for item in sublist] print(flattened) [1, 2, 3, 2, 3, 4, 3, 4, 5]

Si su problema se puede resolver operando en la lista plana, este es un reemplazo efectivo. Contraste estas frases para el ejemplo dado:

all_union = reduce(lambda a, b: set(a).union(set(b)), L) {1, 2, 3, 4, 5} all_union = set([item for sublist in L for item in sublist]) {1, 2, 3, 4, 5}