从dict键列表中查找嵌套的max / min

时间:2015-05-22 21:53:39

标签: python dictionary nested max min

我有一个来自大文件的嵌套键值列表:

mainLs = [{'99999': {'popDensity': 0.0, 'housingDensity': 1.8062141714841409e-07}, '53000': {'popDensity': None, 'housingDensity': None}, '56938': {'popDensity': None, 'housingDensity': None}, '22594': {'popDensity': 0.003762399188257728, 'housingDensity': 0.002336601878903448}, '49194': {'popDensity': 0.0, 'housingDensity': 0.0005159765063886844}, '54232': {'popDensity': 0.0, 'housingDensity': 0.00046439265846193704}, '06000': {'popDensity': None, 'housingDensity': None}, '00562': {'popDensity': 0.0007453821299310868, 'housingDensity': 0.00035915666845218}, '68084': {'popDensity': 0.0, 'housingDensity': 0.0}}]

我想返回一个用户友好的字符串,以便注意popDensity最高的地方。

def find_densest(k, lst):
    placeId = max(lst, key =lambda place: lst[place][k] if place[k])
    ans =  "Densest placeFIPS is " + str(placeId) + " for " + k
    print(ans)

# Expected Output
find_densest('popDensity', mainLs)
>>> "The densest place ID is 22594 with the popDensity of 0.003762399188257728"

我需要保留与键相同位置的多个实例。有没有办法做到这一点?

1 个答案:

答案 0 :(得分:1)

您的密钥功能有两个问题:

lambda density: lst[density][k]

首先,关键函数的参数将是lst的一个元素 - 一个地方dict,而不是密度,或者您可以用作list索引的任何内容。所以:

lambda place: place[k]

这就是导致你当前TypeError的原因;您正尝试将地点dict用作列表的索引。

但是如果你解决了这个问题,你就会遇到另一个问题。您尝试在包含maxfloat的一组值上调用None。这是不明确的,Python不会试图猜测你的意思。 None是否意味着没有人口,所以它应该算作最小或未知人口,所以应该跳过它,或者......什么?一旦您可以用英语解释规则,就可以将其翻译成Python。

例如,这是一个将None视为最低值的关键函数:

place = max(lst, key=lambda place: place[k] if place[k] is not None else -1)

或者,这是一个跳过None值的生成器表达式:

place = max((place for place in lst if place[k] is not None),
            key=lambda place: place[k])

同时,这假设你首先拥有的是一个有效的词典列表。你向我们展示的是SyntaxError,所以你很难猜到你的真实情况。也许是一系列的dicts,或者说是dicts的词典?如果不知道这一点,那么你在迭代你所拥有的东西的方式上肯定会有另一个错误......但是除非我们能够看到你真正拥有的东西,否则无法告诉你如何修复它。

例如,如果你有一个dicts的词典,mainLs中的每个词都只是一个地名,而不是一个地方dict。另一方面,如果它是一个dicts的dicts列表,那么mainLs中的每个东西都将成为一个dict,其唯一的键是一个地名,其唯一值是一个地方dict,在这种情况下,您需要在该值中查找密度,而不是在顶级字典中查找密度。适用于其中一种解决方案的解决方案在没有更改的情况下对其他解决方案不起作用。