这是我(嘴上)的回答:
myDict = reduce(lambda d, t: (d.__setitem__(t[1], d.get(t[1], 0) + t[2]), d)[1], myTupleList, {})
它又丑又坏,但它是这样工作的。
reduce 的第一个参数(因为那里不清楚)是lambda d, t: (d.__setitem__(t[1], d.get(t[1], 0) + t[2]), d)[1]。我稍后会谈到这个,但现在,我将它称为joe(无意冒犯任何名为 Joe 的人)。 reduce 函数基本上是这样工作的:
joe(joe(joe({}, myTupleList[0]), myTupleList[1]), myTupleList[2])
这是一个三元素列表。如您所见,它基本上使用其第一个参数将每个结果累积到最终答案中。在这种情况下,最终的答案就是您想要的字典。
现在是joe 本身。这是joe 作为def:
def joe(myDict, tupleItem):
myDict[tupleItem[1]] = myDict.get(tupleItem[1], 0) + tupleItem[2]
return myDict
不幸的是,= 或 return 在 Python lambda 中不允许使用任何形式,因此必须绕过。我通过直接调用dicts __setitem__ 函数来解决缺少= 的问题。我通过创建一个返回值为__setitem__ 和字典的元组,然后返回包含字典的元组元素来解决缺少返回的问题。我会慢慢修改joe,让你看看我是如何做到的。
首先,删除=:
def joe(myDict, tupleItem):
# Using __setitem__ to avoid using '='
myDict.__setitem__(tupleItem[1], myDict.get(tupleItem[1], 0) + tupleItem[2])
return myDict
接下来,让整个表达式计算为我们想要返回的值:
def joe(myDict, tupleItem):
return (myDict.__setitem__(tupleItem[1], myDict.get(tupleItem[1], 0) + tupleItem[2]),
myDict)[1]
在我的 Python 编程中,我已经多次遇到 reduce 和 dict 这个用例。在我看来,dict 可以使用成员函数reduceto(keyfunc, reduce_func, iterable, default_val=None)。 keyfunc 将从可迭代对象中获取当前值并返回键。 reduce_func 将获取字典中的现有值和可迭代的值并返回字典的新值。如果字典缺少键,default_val 将是传递给 reduce_func 的内容。返回值应该是字典本身,因此您可以执行以下操作:
myDict = dict().reduceto(lambda t: t[1], lambda o, t: o + t, myTupleList, 0)