在词典列表中使用"reduce"

Dig*_*eer 7 python dictionary functional-programming python-itertools

我试图写总结是有钥匙的所有值一个简单的Python函数喜欢.我正在为这项任务进行函数式编程.因此,我需要使用一个列表理解,map,filter,或reduce.在这种情况下,我认为reduce是一个合理的选择.

def sum_favorites(msgs):
     num_favorites = reduce(lambda x, y: x["likes"] + y["likes"], msgs)
     return num_favorites


content1 = {"likes": 32, ...}
content2 = {"likes": 8, ...}
content3 = {"likes": 16, ...}
contents = [content1, content2, content3]
print(sum_favorites(contents)) 
Run Code Online (Sandbox Code Playgroud)

问题出现在我实际运行代码时.我似乎收到了类似的东西:TypeError:'int'对象不可订阅.对我来说,这个错误毫无意义.如果reduce是通过给定的参数真正迭代,然后传递到λ-功能的每个项目应该是一个字典-他们每个人肯定有一个喜欢在他们的关键.问题是什么,这个Python错误究竟是什么意思?

hob*_*bbs 16

对我来说,这个错误毫无意义.如果reduce实际上是遍历给定参数,那么传入lambda函数的每个项应该是一个字典

不,传递给lambda 的第一个参数(对于除第一个之外的所有调用)是前一次调用lambda的返回值.您的函数返回一个数字,因此它将x作为数字而不是字典来调用.

有两种方法可以解决这个问题.可能更直接的是:

num_favorites = reduce(lambda x, y: x + y['likes'], msgs, 0)
Run Code Online (Sandbox Code Playgroud)

0是reduce的"初始化器"参数,它提供了第一个值x.现在在每个调用中,x是运行总和并且y是下一个字典.

另一种方式,只是为了表明它可以做到,是:

result = reduce(lambda x, y: { 'likes': x['likes'] + y['likes'] }, msgs)
num_favorites = result['likes']
Run Code Online (Sandbox Code Playgroud)

这使得lambda的返回值成为带有likes键的dict ,就像它的参数一样,所以我们在整个过程中使用相同的类型.在这种情况下,它是不必要的和浪费的,但如果你聚合了多个密钥,它可能是一个有趣的方法.


Evg*_*kin 6

在您的代码片段中reduce(lambda x, y: x["likes"] + y["likes"], msgs)x变量首先是列表 msgs ( ) 的第一个元素,但在第二次迭代时它将是( )dict的总和。"likes"int

因此,要总结喜欢,请使用函数docinitializer的参数。reduce

def sum_favorites(msgs):
    num_favorites = reduce(lambda x, y: x + y["likes"], msgs, 0)
    return num_favorites
Run Code Online (Sandbox Code Playgroud)

但我相信,使用sum是一种更Pythonic的方式:

def sum_favorites(msgs):
    num_favorites = sum(i['likes'] for i in msgs)
    return num_favorites
Run Code Online (Sandbox Code Playgroud)