从两个现有的词组

时间:2016-11-29 20:34:49

标签: python dictionary collections

我有两个已设置为值的dicts。

Dct1 = {'a':[1, 2, 3], 'b':[4, 5, 6, 7], 'c':[8, 9, 10], 'd':[11, 12, 13, 14]}
Dct2 = {'TypeZ':['a', 'b'], 'TypeX':['c', 'd']}

我想创建另一个词典: 1.遍历Dct1中值的项目 2.检查项目值的键是否为Dct2值中的项目 3.使用dct2的键作为新dct的键,并使用dict中值的相应项作为新dict的设置值

Dct3 = {'TypeZ':[1, 2, 3, 4, 5, 6, 7], 'TypeX':[8, 9, 10, 11, 12, 13, 14]}

我还想避免在Dct3的值中重复。

以下是我目前正在努力解决的代码片段(其他代码已成功构建):

RateByType = {}

for key, item in RoRaDct.items():
    for i, j in TpRtDct.items():
        for x in item:
            for y in j:
                if key == y:
                    RateByType[i].add(item)

但它产生了一个关键错误。我尝试过使用defaultdict(set)但得到一个TypeError:unhashable类型:set。后者是我用来构建前两个dicts的方法。

2 个答案:

答案 0 :(得分:1)

设置gc()个密钥,然后为Dct2创建defaultdict,循环使用Dct3个密钥及其密钥相应的值:

Dct2

结果:

import collections
Dct1 = {'a':[1,2,3],'b':[4,5,6,7],'c':[8,9,10],'d':[12,12,13,14]}
Dct2 = {'TypeZ':['a','b'],'TypeX':['c','d']}
s = set(Dct2)
d = collections.defaultdict(list)
for key in Dct2:
    for k in Dct2[key]:
        d[key].extend(Dct1[k])

答案 1 :(得分:0)

Dct3 = {k: set.union(*map(lambda x: set(Dct1.get(x, [])), v)) for k, v in Dct2.items()}

对于Dct2中的每个键值对,我们将键映射到由Dct1中键的值的成员元素映射到的集合的并集。

编辑:解释

{k: v for k, v in Dct2.items()}

dictionary comprehension,可重新创建Dct2

set.union(*map(lambda x: set(Dct1.get(x, [])), v))

我们正在使用什么来构建集合,但让我们从内到外看看它。

Dct1.get(x, [])

尝试访问Dct1[x]并返回它。如果dict没有键x,则返回空列表[]

set(Dct1.get(x, []))

获取上面Dct1.get的结果并将其转换为集合。

lambda x: set(Dct1.get(x, []))

定义匿名函数(即它没有名称)。该函数只接受输入x并使用它来计算表达式set(Dct1.get(x, []))

map(lambda x: set(Dct1.get(x, [])), v)

map是一个函数,它接受另一个函数(在本例中是我们的lambda函数)和一个可迭代的(如列表),然后创建一个迭代,将该函数应用于输入可迭代的每个元素。

*map(lambda x: set(Dct1.get(x, [])), v)

此上下文中的*运算符用于解包迭代。因此,它需要像[1, 2, 3]这样的迭代,并将add(*[1, 2, 3])变为add(1, 2, 3)

 set.union(*map(lambda x: set(Dct1.get(x, [])), v))

set.union是一个函数,它接受多个集合并计算它们的并集,基本上将它们全部加在一起。