给出字典列表,例如:
history = [
{
"actions": [{"action": "baz", "people": ["a"]}, {"action": "qux", "people": ["d", "e"]}],
"events": ["foo"]
},
{
"actions": [{"action": "baz", "people": ["a", "b", "c"]}],
"events": ["foo", "bar"]
},
]
获取字典列表的最有效方法(虽然仍然可读)是什么,其中每个字典是唯一的event
,并且基于{{1} }键。例如,对于上面的列表,所需的输出是:
action
我无法更改输出结构,因为它已被外部设备消耗。我编写了下面的代码,该代码可以工作,但是非常冗长且可读性很差。
output = [
{
"event": "foo",
"actions": [
{"action": "baz", "people": ["a", "b", "c"]},
{"action": "qux", "people": ["d", "e"]}
]
},
{
"event": "bar",
"actions": [
{"action": "baz", "people": ["a", "b", "c"]}
]
},
]
我只针对python3.6 +
答案 0 :(得分:2)
您可以将collections.defaultdict
与itertools.groupby
一起使用:
from collections import defaultdict
from itertools import groupby as gb
d = defaultdict(list)
for i in history:
for b in i['events']:
d[b].extend(i['actions'])
new_d = {a:[(j, list(k)) for j, k in gb(sorted(b, key=lambda x:x['action']), key=lambda x:x['action'])] for a, b in d.items()}
result = [{'event':a, 'actions':[{'action':c, 'people':list(set([i for k in b for i in k['people']]))} for c, b in d]} for a, d in new_d.items()]
输出:
[
{'event': 'foo',
'actions': [
{'action': 'baz', 'people': ['b', 'a', 'c']},
{'action': 'qux', 'people': ['d', 'e']}
]
},
{'event': 'bar',
'actions': [{'action': 'baz', 'people': ['b', 'a', 'c']}]
}
]
答案 1 :(得分:0)
答案不是那么冗长,但可读性更好。此外,它不依赖于其他任何东西,而只是标准的python。
tmp_dict = {}
for d in history:
for event in d["events"]:
if event not in tmp_dict:
tmp_dict[event] = {}
for actions in d["actions"]:
tmp_dict[event][actions["action"]] = actions["people"]
else:
for actions in d["actions"]:
if actions["action"] in tmp_dict[event]:
tmp_dict[event][actions["action"]].extend(actions["people"])
else:
tmp_dict[event][actions["action"]] = actions["people"]
output = [{"event": event, "actions": [{"action": ac, "people": list(set(peop))} for ac, peop in tmp_dict[event].items()]} for event in tmp_dict]
print (output)
输出:
[
{'event': 'foo',
'actions': [
{'action': 'qux', 'people': ['e', 'd']},
{'action': 'baz', 'people': ['a', 'c', 'b']}
]
},
{'event': 'bar',
'actions': [{'action': 'baz', 'people': ['a', 'c', 'b']}]
}
]