基于重复值从字典创建嵌套字典

时间:2018-06-04 15:30:57

标签: python python-3.x dictionary

我是Python(3.6)的新手,我正试图想出一种从列表列表中创建嵌套字典的方法。示例输入是:

myList = [[1, B, C],[1, D, C],[1, E, C],[1, F, G],[1, H, G],[2, I, C],[2, J, C],[2, K, G]]

我想得到的是:

result = {1: {C: [B, D, E], G: [F, H]}, 2: {C: [I, J], G: [K]}}

我现在得到的是:

result = defaultdict(list)
for key, *values in myList:
    result[key].extend(values)

这给了我输出:

{1: [B, C, D, C, E, C, F, G, H, G], 2: [I, C, J, C, K, G]}

我正在寻找一种创建嵌套字典的方法,其中键值列表中的每个重复值都成为子字典的键。您是否可以建议我考虑哪些方法可以考虑我正在处理大型数据集?到目前为止我所做的工作有一个重大缺陷,因为我放弃了哪些值应该分配给子词典中哪个键的信息。

2 个答案:

答案 0 :(得分:3)

您可以在此处使用defaultdict,但只是通过list无法正常工作,因为您不想要一个值为列表的字典;你想要一个值为dicts的dict,每个dict的值都是列表。因此,您必须将defaultdict的第二层传递给第一层defaultdict

from collections import defaultdict

seq = [[1, 'B', 'C'],[1, 'D', 'C'],[1, 'E', 'C'],[1, 'F', 'G'],[1, 'H', 'G'],[2, 'I', 'C'],[2, 'J', 'C'],[2, 'K', 'G']]
d = defaultdict(lambda: defaultdict(list))
for key1, value, key2 in seq:
    d[key1][key2].append(value)

print(d)

结果:

defaultdict(<function <lambda> at 0x00DEC6A8>, {1: defaultdict(<class 'list'>, {'C': ['B', 'D', 'E'], 'G': ['F', 'H']}), 2: defaultdict(<class 'list'>, {'C': ['I', 'J'], 'G': ['K']})})

......对于{1: {'C': ['B', 'D', 'E'], 'G': ['F', 'H']}, 2: {'C': ['I', 'J'], 'G': ['K']}}

,这与项目明确相同

答案 1 :(得分:1)

您可以使用递归的itertools.groupby来处理具有任意长度的子列表的输入:

import itertools
keys = [[lambda x:x[0], lambda x:x[1:]], [lambda x:x[-1], lambda x:x[:-1]]]
l = [[1, 'B', 'C'],[1, 'D', 'C'],[1, 'E', 'C'],[1, 'F', 'G'],[1, 'H', 'G'],[2, 'I', 'C'],[2, 'J', 'C'],[2, 'K', 'G']]
def group_result(d, keys):
  k, splice = keys[0]
  c = {a:[splice(i) for i in b] for a, b in itertools.groupby(sorted(d, key=k), key=k)}
  return {a:group_result(b, keys[1:]) if keys[1:] else [i for c in b for i in c] for a, b in c.items()}

print(group_result(l, keys))

输出:

{1: {'C': ['B', 'D', 'E'], 'G': ['F', 'H']}, 2: {'C': ['I', 'J'], 'G': ['K']}}