【发布时间】:2020-05-28 23:28:10
【问题描述】:
处理字典列表和避免副作用(什么是副作用)的最 Pythonic 和最有效的方法是什么?
更具体地说:为什么以下代码会生成生成器对象,而几乎任何其他类似的代码都会生成所需的输出?
print(sum(dictionary[site] for site in dictionary) for dictionary in listofdictionaries)
一些背景
我从摆弄**kwargs 开始,并生成了我认为非常糟糕的代码。
def testing(**kwargs):
mysum = 0
for kw in kwargs:
mysum += kwargs[kw]
print(mysum)
listofdictionaries = [{"site1": 1, "room1": 2, "day1": 3}, {"site2": 4, "room2": 5, "day2": 6}]
for dictionary in listofdictionaries:
testing(**dictionary)
我查看了 Data Structures Document 包括 List Comprehension 并找到了实现相同输出的更好方法:
listofdictionaries = [{"site1": 1, "room1": 2, "day1": 3}, {"site2": 4, "room2": 5, "day2": 6}]
for dictionary in listofdictionaries:
mysum = 0
for value in dictionary:
mysum += dictionary[value]
print(mysum)
然后变得有点聪明,并缩短了一点:
for dictionary in listofdictionaries:
print(sum(dictionary[value] for value in dictionary))
我真的没有兴趣为了使它成为单线而使其成为单线,但是在阅读了 Stack Overflow 上无数关于避免“副作用”的列表理解帖子之后,我觉得可能有采取这一措施的额外步骤。也许我不明白什么是副作用。
无论如何,这些中的每一个都应该导致输出:
6
15
【问题讨论】:
-
您的代码没有副作用。副作用就像改变数据结构、分配给变量、打印到标准输出或写入文件。
-
因此,例如,您的 for 循环使用副作用,
mysum += dictionary[value]修改了mysum变量。但这没关系,python 是一种按设计以这种方式工作的命令式语言。列表推导及其表亲是函数式编程结构,旨在表达映射/过滤操作,这就是为什么它们应该没有副作用。
标签: python python-3.x list-comprehension nested-loops