每当我使用lambda表达式时,我都会得到这个pep8警告。不建议使用lambda表达式吗?如果不是,为什么?
当前回答
我还遇到过一种情况,在这种情况下,甚至不可能使用已定义的函数。
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},
}
在这种情况下,我真的想做一个属于类的映射。映射中的某些对象需要相同的函数。将a命名函数放在类之外是不合逻辑的。 我还没有找到从类主体内部引用方法(staticmethod, classmethod或normal)的方法。当代码运行时,SomeClass还不存在。所以从类中引用它也是不可能的。
其他回答
你在PEP-8中遇到的建议是:
Always use a def statement instead of an assignment statement that binds a lambda expression directly to a name. Yes: def f(x): return 2*x No: f = lambda x: 2*x The first form means that the name of the resulting function object is specifically 'f' instead of the generic '<lambda>'. This is more useful for tracebacks and string representations in general. The use of the assignment statement eliminates the sole benefit a lambda expression can offer over an explicit def statement (i.e. that it can be embedded inside a larger expression)
将lambdas分配给名称基本上只是重复了def的功能——通常情况下,最好使用单一的方法来避免混淆并增加清晰度。
lambda的合法用例是你想使用一个函数而不给它赋值,例如:
sorted(players, key=lambda player: player.rank)
一般来说,反对这样做的主要理由是def语句将导致更多代码行。我对此的主要回答是:是的,这很好。除非你在打代码高尔夫,否则尽量减少行数不是你应该做的事情:追求清晰而不是简短。
我还遇到过一种情况,在这种情况下,甚至不可能使用已定义的函数。
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},
}
在这种情况下,我真的想做一个属于类的映射。映射中的某些对象需要相同的函数。将a命名函数放在类之外是不合逻辑的。 我还没有找到从类主体内部引用方法(staticmethod, classmethod或normal)的方法。当代码运行时,SomeClass还不存在。所以从类中引用它也是不可能的。
Lattyware是绝对正确的:基本上PEP-8希望你避免这样的事情
f = lambda x: 2 * x
而是使用
def f(x):
return 2 * x
然而,正如在最近的bugreport(2014年8月)中所述,以下语句现在是合规的:
a.f = lambda x: 2 * x
a["f"] = lambda x: 2 * x
由于我的PEP-8检查器还没有正确地实现这一点,我暂时关闭了E731。
故事是这样的,我有一个简单的函数我用了两次。
a = map(lambda x : x + offset, simple_list)
b = map(lambda x : x + offset, another_simple_list)
这只是表示法,我遇到过几个不同的版本。
现在,为了保持干燥,我开始重用这个常见的lambda。
f = lambda x : x + offset
a = map(f, simple_list)
b = map(f, another_simple_list)
在这一点上,我的代码质量检查抱怨lambda是一个命名函数,所以我把它转换成一个函数。
def f(x):
return x + offset
a = map(f, simple_list)
b = map(f, another_simple_list)
现在检查器抱怨一个函数前后必须有一个空行。
def f(x):
return x + offset
a = map(f, simple_list)
b = map(f, another_simple_list)
现在我们有6行代码而不是原来的2行,可读性没有增加,python化也没有增加。此时,代码检查器抱怨函数没有文档字符串。
在我看来,最好避免这个规则,当它有意义时,使用你的判断。
这适用于我在一个类,删除lambda表达式和使用def代替,改变这个…
def set_every(self, every: int = 1, time_unit: int = TimeUnit.Day):
every_func = lambda x: "*" if x == 1 else "*/" + str(x)
if TimeUnit.has_value(time_unit):
self.month_of_year = "*"
self.day_of_month = "*" if time_unit != TimeUnit.Day else every_func(every)
self.day_of_week = "*" if time_unit != TimeUnit.Week else every_func(every)
由这个……
def set_every(self, every: int = 1, time_unit: int = TimeUnit.Day):
def every_func(x: int) -> str: return "*" if x == 1 else "*/" + str(x)
if TimeUnit.has_value(time_unit):
self.month_of_year = "*"
self.day_of_month = "*" if time_unit != TimeUnit.Day else every_func(every)
self.day_of_week = "*" if time_unit != TimeUnit.Week else every_func(every)
推荐文章
- 将Pandas或Numpy Nan替换为None以用于MysqlDB
- 使用pandas对同一列进行多个聚合
- 使用Python解析HTML
- django MultiValueDictKeyError错误,我如何处理它
- 如何在for循环期间修改列表条目?
- 我如何在Django中创建一个鼻涕虫?
- 没有名为'django.core.urlresolvers'的模块
- 蟒蛇导出环境文件
- Django - makemigrations -未检测到任何更改
- SQLAlchemy:引擎、连接和会话差异
- 在Python Pandas中删除多个列中的所有重复行
- 更改pandas DataFrame中的特定列名
- 将Pandas多索引转换为列
- 熊猫在每组中获得最高的n个记录
- 熊猫数据帧得到每组的第一行