如果您将dict()添加到Max Chrétiens上面的不错的简短解决方案中,您最终将得到常规字典:
data3 = {k1: dict(Counter(v1) + Counter(v2)) for (k1, v1), (k2, v2) in
zip(data1.items(), data2.items())}
然而,这仅在两个字典共享完全相同的键时才能正常工作,如上所述。如果两个字典之间存在任何不共享的键,Willem Van Onsem的解决方案将无法正常工作(它将导致错误),而Max Chrétiens的解决方案在这种情况下会错误地合并项目。现在你提到你正在使用始终包含类似键结构的JSON数据,因此这不应构成问题,Max Chrétien的解决方案应该可以很好地工作。
如果您确实希望确保仅使用两个字典(及其子字典)共享的键,请使用以下内容。请注意,我将“X”:111111作为键值对添加到了2012子字典中,并添加了“1999”:{'Z':999999}作为整个子字典。
def sum_two_nested_dicts(d1, d2):
dicts = [d1, d2]
d_sum = {}
for topkey in dicts[0]:
if topkey in dicts[1]:
d_sum[topkey] = {}
for key in dicts[0][topkey]:
if key in dicts[1][topkey]:
new_val = sum([d[topkey][key] for d in dicts])
d_sum[topkey][key] = new_val
return d_sum
data1 = {
"2010": {
'A': 2,
'B': 3,
'C': 5
},
"2011": {
'A': 1,
'B': 2,
'C': 3
},
"2012": {
'A': 1,
'B': 2,
'C': 4,
'X': 111111
},
"1999": {
'Z': 999999
}
}
data2 = {
"2010": {
'A': 4,
'B': 4,
'C': 5
},
"2011": {
'A': 1,
'B': 1,
'C': 3
},
"2012": {
'A': 3,
'B': 2,
'C': 4
}
}
data3 = sum_two_nested_dicts(data1, data2)
print(data3)
data4 = sum_two_nested_dicts(data2, data1)
print(data4)
我知道这并不像能够更加简明优雅的代码那样,但是既然我已经写了,我就在这里发布,以便有人想要实现这种特定功能时可以参考。
这是一个冗长而臃肿的版本,保留了未共享的键/值,仅因为我已经写过了...
def sum_nested_dicts(dic1, dic2):
dicts = [dic1, dic2]
topkeys = set(sum([list(dic.keys()) for dic in dicts], []))
d_sum = {}
for topkey in topkeys:
if topkey in dic1 and topkey in dic2:
d_sum[topkey] = {}
keys = set(sum([list(dic[topkey].keys()) for dic in
dicts], []))
for key in keys:
if key in dic1[topkey] and key in dic2[topkey]:
new_val = sum([d[topkey][key] for d in dicts])
d_sum[topkey][key] = new_val
elif key in dic1[topkey]:
d_sum[topkey][key] = dic1[topkey][key]
elif key in dic2[topkey]:
d_sum[topkey][key] = dic2[topkey][key]
elif topkey in dic1:
d_sum[topkey] = dic1[topkey]
elif topkey in dic2:
d_sum[topkey] = dic2[topkey]
return d_sum
看看Crystal的解决方案,似乎是迄今为止发布的最简洁和功能最强大的解决方案。