我在谷歌上搜索过并尝试过各种方法(通常是在itertools.groupby()
)来实现这一点,但我显然没有正确的思考方法,所以我真的很高兴能得到一些帮助。我需要将主机名键合并到主机名列表中,所有其他键都匹配
所以我有一个目录:
MyList = [
{'hostname': 'ABC', 'servicecheck': 'The roof is on fire', 'state': 'prettybad' },
{'hostname': 'DEF', 'servicecheck': 'The roof is on fire', 'state': 'prettybad' },
{'hostname': 'GHI', 'servicecheck': 'The roof is on fire', 'state': 'prettybad' },
{'hostname': 'ABC', 'servicecheck': 'The sky is blue', 'state': 'notsobad' },
{'hostname': 'ABC', 'servicecheck': 'The birds are pretty', 'state': 'prettybad' }
]
当其他键匹配时,我需要根据主机名合并它们,即:
GroupedList = [
{'hostnames': ['ABC','DEF','GHI'], 'servicecheck': 'The roof is on fire', 'state': 'prettybad' },
{'hostname': 'ABC', 'servicecheck': 'The sky is blue', 'state': 'notsobad' },
{'hostname': 'ABC', 'servicecheck': 'The birds are pretty', 'state': 'prettybad' }
]
您可以合并dict作为
itertools.groupby()
的后续操作。下面的解决方案很大程度上依赖于解包操作符,而解包操作符并不总是直观的,只能在一行中工作,但我会尽力解释首先,我们使用列表理解来循环
itertools.groupby()
中的组。您可以提供一个自定义键(我已经这样做了),通过'servicecheck'
和'state'
键对相邻元素进行分组(如果您希望能够捕获和分组无序的事件,您可以首先调用sorted()
并使用相同的键)然后,我们使用另一个列表理解将组成每个组的迭代器从
groupby()
转换为列表,这样我们可以在表达式中多次使用它们,这是我们需要做的接下来,我们为每个组创建一个dict。这不是dict理解,而是一个有趣的习惯用法,它使用解包操作符
**
将一个dict转换为另一个dict(基本上,编写dict文本,但从现有dict获取键和值)。因此表达式{**lst[0]}
生成了一个新的dict,但复制了lst[0]
中的键和值。请注意,除了'hostname'
之外的所有键和值在组中的所有对象之间都是相同的然后,我们在同一文本中覆盖
'hostname'
键,从而适应这种情况-在这里,我们只是从列表中拉出所有不同的主机名,并将它们粘贴到一个列表中,我们将其分配给原始主机名所以这个表达式
{**lst[0], 'hostname': [d['hostname'] for d in lst]}
在功能上等同于我们对每个小组都这样做,以得到我们的答案
(如果希望输出中的第二项和第三项是字符串而不是单例列表,则可以替换
与
)
相关问题 更多 >
编程相关推荐