对项目列表的字典操作



我有字典

{ 'a': 1.0,
  'b': 1.1,
  'c': 0.9,
  # ...
  'z': 0.97
}

我有一个项目清单说['a', 'b', 'c'].我想从字典中找到此列表值的平均值。当然,我可以遍历我的列表,查找并求和值,但是有没有办法在没有 for 循环的情况下获得它?

你必须

有一个循环。但是,您可以隐藏循环。

您可以使用 operator.itemgetter() 对象为您执行此操作,例如:

from operator import itemgetter
average = sum(itemgetter(*list_of_keys)(your_dictionary)) / len(list_of_keys)

绝对明确地说:itemgetter()现在循环访问您的键列表并生成具有相应值的元组。

另一个"隐藏"循环是map()函数;使用 dict.get()dict.__getitem__() 作为要映射到的函数,map()再次为您完成所有循环:

avegare = sum(map(your_dictionary.__getitem__, list_of_keys)) / len(list_of_keys)

这里dict.getdict.__getitem__之间的区别在于,当缺少密钥时,您会得到什么结果; 当您最终尝试将None和数字相加时,第一个将导致TypeError,另一个将为您提供KeyError

否则,只需在生成器表达式中使用循环:

average = sum(your_dictionary[k] for k in list_of_keys) / len(list_of_keys)

演示:

>>> from operator import itemgetter
>>> d = {'a': 1.0, 'z': 0.97, 'c': 0.9, 'b': 1.1}
>>> selected = ['a', 'b', 'c']
>>> sum(itemgetter(*selected)(d)) / len(selected)
1.0
>>> sum(map(d.__getitem__, selected)) / len(selected)
1.0
>>> sum(d[k] for k in selected) / len(selected)
1.0

如果你使用的是python3,你可以使用statistics.mean:

d = { "a": 1.0,
  "b": 1.1,
  "c": 0.9,
  "z": 0.97
}
lst = ["a", "b", "c"]
from statistics import mean

print(mean(map(d.get, lst)))

或者只使用总和:

print(sum(map(d.get, lst)) / len(lst))

这假定 lst 中的所有项目都在字典中,否则您将在添加浮点数和 NoneType 时出错。

如果你的字典被称为values,你的列表被称为items,有一个非常简短的解决方案:

arithmetic_mean_inexact = sum(values[i] for i in items) / len(items)

请注意,这不支持空items列表,因为这将导致ZeroDivisionError。 这很好,因为空序列的平均值并没有真正的意义。

虽然此解决方案表明可以在没有显式 for 循环的情况下计算平均值,但它存在一个问题,即对大量浮点数求和并将其除以大数可能会导致数值精度损失。 解决这个问题并非易事,需要更长的解决方案。 幸运的是,Python 3.4(或更高版本)为此提供了统计模块,因此您应该使用statistics.mean()(正如另一个答案已经提出的那样)。 例如:

from statistics import mean
arithmetic_mean = mean([values[i] for i in items])

根据您的具体问题,此函数中的其他函数可能更合适。 您可以在统计模块的文档中找到更多信息。

最新更新