我如何将一个字典列表组合到一个组合类似键的字典列表

How can i combine a list of dicts to a list of dicts combining like keys

我想接受这个输入:

mycounter = [{6: ['Credit card']}, {2: ['Debit card']}, {2: ['Check']}]                                                                                                                                                        
#[{6: ['Credit card']}, {2: ['Debit card']}, {2: ['Check']}]

并实现此预期输出:

[{6: ['Credit card']}, {2: ['Debit card', 'Check']}]

我的尝试如下,但它与所需的输出不匹配。在这里的任何帮助表示赞赏。谢谢

temp = list(zip([*map(lambda d: next(iter(d.keys())), mycounter)], [*map(lambda d: next(iter(d.values())), mycounter)]))  

c = collections.defaultdict(list)
for a,b in temp:
   c[a].extend(b)

final = [dict(c)]
# Close, but not quite the desired output since it's should be two dict objects, not one
# [{6: ['Credit card'], 2: ['Debit card', 'Check']}]

我在 Whosebug 上的搜索找到了与提供 None 值相结合的解决方案,但与我要求的完全不同。我的问题与之前另一个类似问题的输入不同。

一个选择是制作一个字典,然后在以下之后将其分解为单个键值对:

mycounter = [{6: ['Credit card']}, {2: ['Debit card']}, {2: ['Check']}]                                                                                                                                                        

res = {}
for d in mycounter:
    for k, v in d.items():
        res.setdefault(k, []).extend(v)
[{k:v} for k, v in res.items()]
# [{6: ['Credit card']}, {2: ['Debit card', 'Check']}]

这与非常相似;唯一的区别是您希望每个 key/value 对都在自己的字典中。这是一个使用理解和 itertools 的改编解决方案:

from itertools import chain

def merge_dicts(*dicts):
    return [
        { k: list(chain.from_iterable( d[k] for d in dicts if k in d )) }
        for k in set(chain.from_iterable(dicts))
    ]

为了提供选项,这里有一个使用 defaultdict 的替代版本,我发现它更容易使用,尤其是随着复杂性的增加:

from collections import defaultdict
result = defaultdict(list)
for d in mycounter:
    for k, v in d.items():
        result[k] += v

In : result
Out: defaultdict(list, {6: ['Credit card'], 2: ['Debit card', 'Check']})

Defaultdict 在大多数情况下表现得像 dict,但如有必要,可以将其转换为:

In : dict(result)
Out: {6: ['Credit card'], 2: ['Debit card', 'Check']}