Pregunta

Recibo esta advertencia de pep8 cada vez que uso expresiones lambda.¿No se recomiendan las expresiones lambda?Si no ¿por qué?

¿Fue útil?

Solución

La recomendación en PEP-8 te estás encontrando es:

Siempre use una declaración DEF en lugar de una declaración de asignación que une una expresión de Lambda directamente a un nombre.

Sí:

def f(x): return 2*x 

No:

f = lambda x: 2*x 

La primera forma significa que el nombre del objeto de función resultante es específicamente 'f' en lugar del genérico 'u003Clambda> '.Esto es más útil para trazas y representaciones de cadenas en general.El uso de la declaración de asignación elimina el beneficio único que una expresión de lambda puede ofrecer en una declaración de DEF explícita (es decirque se puede incrustar dentro de una expresión más grande)

Asignar lambdas a nombres básicamente simplemente duplica la funcionalidad de def - y, en general, es mejor hacer algo de una sola manera para evitar confusiones y aumentar la claridad.

El caso de uso legítimo de lambda es cuando desea utilizar una función sin asignarla, por ejemplo:

sorted(players, key=lambda player: player.rank)

Para operaciones simples, el operator módulo proporciona algunas opciones útiles en attrgetter, itemgetter y methodcaller que a menudo puede reemplazar labmdas que solo acceden a atributos, elementos y métodos de llamada.

Por ejemplo, lo anterior se podría hacer con operator.attrgetter al igual que:

sorted(players, key=operator.attrgetter('rank'))

Otros consejos

Aquí está la historia, tuve una simple función de lambda que estaba usando dos veces.

a = map(lambda x : x + offset, simple_list)
b = map(lambda x : x + offset, another_simple_list)

Esto es solo para la representación, me he enfrentado a un par de versiones diferentes de esto.

Ahora, para mantener las cosas secas, empiezo a reutilizar esta lambda común.

f = lambda x : x + offset
a = map(f, simple_list)
b = map(f, another_simple_list)

En este punto, mi verificador de calidad de código se queja de que Lambda sea una función con nombre, así que lo convermo en una función.

def f(x):
    return x + offset
a = map(f, simple_list)
b = map(f, another_simple_list)

Ahora, el corrector se queja de que una función debe estar limitada por una línea en blanco antes y después.

def f(x):
    return x + offset

a = map(f, simple_list)
b = map(f, another_simple_list)

Aquí tenemos 6 líneas de código en lugar de líneas originales 2 sin aumento de la legibilidad y sin aumento de ser Pythonic.En este punto, el comprobante de código se queja de la función que no tiene documentos de documentos.

En mi opinión, esta regla sea mejor evitada y rota cuando tenga sentido, usa su juicio.

lattyware es absolutamente correcto: básicamente PEP-8 quiere que evite las cosascomo

f = lambda x: 2 * x

y en su lugar usar

def f(x):
    return 2 * x

Sin embargo, como se dirigió en una bogreport (ago 2014), ahora son compatibles las declaraciones como las siguientes:

a.f = lambda x: 2 * x
a["f"] = lambda x: 2 * x

Dado que mi comprobante PEP-8 no implementa esto correctamente, desactivé E731 por el momento.

También encontré una situación en la que era incluso imposible usar una función DEF (INED).

class SomeClass(object):
  # pep-8 does not allow this
  f = lambda x: x + 1  # NOQA

  def not_reachable(self, x):
    return x + 1

  @staticmethod
  def also_not_reachable(x):
    return x + 1

  @classmethod
  def also_not_reachable(cls, x):
    return x + 1

  some_mapping = {
      'object1': {'name': "Object 1", 'func': f},
      'object2': {'name': "Object 2", 'func': some_other_func},
  }

En este caso, realmente quería hacer un mapeo que pertenecía a la clase.Algunos objetos en el mapeo necesitan la misma función.Sería ilógico poner la función nombrada fuera de la clase. No he encontrado una manera de referirse a un método (StaticMethod, ClassMethod o Normal) desde el interior del cuerpo de la clase.Someclass no existe todavía cuando se ejecuta el código.Tampoco referirse a él de la clase tampoco es posible.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top