python zip()
Diferencia entre un bucle "for" y un mapa (3)
Citando la documentation
Devuelve un iterador que aplica la función a cada elemento de iterable, produciendo los resultados.
lo que significa que debe recopilar el iterador, por ejemplo
list(map(D.attach_item, items))
> [None, None, None, None]
Hmmm, extraño. Por qué ninguno, ninguno, ...
Sí, puedes convertir cualquier ciclo en una declaración de mapa, pero no siempre es útil. Map toma un parámetro y hace algo con él (en la mayoría de los casos) y lo devuelve, ¡sin efectos secundarios! Aquí hay un ejemplo:
def add(a):
return a + 3
list(map(add, items))
> [4, 5, 6, 7]
El verdadero poder viene cuando lo combinas con otras funciones como filter
def add(a):
return a + 3
def odd(a):
return a % 2 == 1
list(map(add, filter(odd, items)))
> [4, 6]
Del título, sí, hay una diferencia. Ahora aplicado a mi escenario: consideremos un Dummy
clase:
class Dummy:
def __init__(self):
self.attached = []
def attach_item(self, item):
self.attached.append(item)
Si uso esto:
D = Dummy()
items = [1, 2, 3, 4]
for item in items:
D.attach_item(item)
De hecho, recibo D.attached = [1, 2, 3, 4]
. Pero si mapeo la función attach_item
a los items
, D.attached
permanece vacío.
map(D.attach_item, items)
¿Qué está haciendo?
Una pregunta muy interesante que tiene una respuesta interesante.
La función de map
devuelve un objeto Map que es iterable. map
está realizando su cálculo de forma perezosa para que la función no se invoque a menos que itere ese objeto.
Entonces si lo haces:
x = map(D.attach_item, items)
for i in x:
continue
El resultado esperado aparecerá.
map
solo crea un iterador. Debería iterar a través de él para agregar elementos en D.attached
. Me gusta esto:
D = Dummy()
items = [1, 2, 3, 4]
list(map(D.attach_item, items))
Sí, no lo hagas en tu código :) Pero un ejemplo es útil para entender.