如何在Python中将嵌套字典中的2个键/值上移一个级别

时间:2019-05-16 10:04:50

标签: python arrays list dictionary nested

昨天我在这里重新整理字典列表时遇到了一个问题(我提到是为了帮助其他有类似问题的人)

Re-structuring a list of Python Dicts using setdefault

但是,我省略了一部分数据(现在看来很关键)。最初,我认为以后再添加额外的字典键会很容易,但是事实证明,这种结构存在麻烦。因此,我想出了以下方法来接近我的要求。

从本质上讲,我希望将2个键“ selection_id”和“ other_data”上移并完全替换“ market_data”字典(请参见下面的理想数据结构)。

我以为我可以找到一种使用setattr的方法,但是在循环中,使用嵌套字典似乎是有问题的。同样,我什至不确定这是否合适,因为我会以错误的格式接收所有数据。

我的示例代码如下所示:

market=[{'selection_id': 1099,'value':'11', 'value_name': 'a', 'other_data': 89},  
{'selection_id': 1099,'value':'78', 'value_name': 'p', 'other_data': 89},  
{'selection_id': 1097,'value':'39', 'value_name': 'b', 'other_data': 89},  
{'selection_id': 1097,'value':'52', 'value_name': 'f', 'other_data': 89},  
{'selection_id': 1098,'value':'98', 'value_name': 'd', 'other_data': 89},  
{'selection_id': 1099,'value':'13', 'value_name': 'y', 'other_data': 89},  
{'selection_id': 1098,'value':'4', 'value_name': 'r', 'other_data': 89},
]

new_structure = {}  

new_structure2 = []  


for z in market:
        new_structure.setdefault((z['selection_id'], z['other_data']), []).append({'value': z['value'], 'value_name': z['value_name']})
new_structure2.append([{'market_data': m, 'value_dict': n} for m, n in new_structure.items()])

for s in new_structure2:
    for t in s:
        dict = {}
        dict['selection_id'] = t['market_data'][0]
        dict['other_data'] = t['market_data'][1]
        t['market_data'] = dict

print(new_structure2)

上面的代码产生以下内容:

[[{'market_data':  
{'selection_id': 1099, 'other_data': 89}, 'value_dict':  
[{'value': '11', 'value_name': 'a'}, {'value': '78', 'value_name': 'p'}, {'value': '13', 'value_name': 'y'}]},  
{'market_data':  
{'selection_id': 1097, 'other_data': 89}, 'value_dict':  
[{'value': '39', 'value_name': 'b'}, {'value': '52', 'value_name': 'f'}]}, {'market_data':  
{'selection_id': 1098, 'other_data': 89}, 'value_dict':  
[{'value': '98', 'value_name': 'd'}, {'value': '4', 'value_name': 'r'}]}]]

我正在寻找的是:

[{'selection_id': 1099, 'other_data': 89, 'value_dict':  
[{'value': '11', 'value_name': 'a'}, {'value': '78', 'value_name': 'p'}, {'value': '13', 'value_name': 'y'}]},  
{'selection_id': 1097, 'other_data': 89, 'value_dict':  
[{'value': '39', 'value_name': 'b'}, {'value': '52', 'value_name': 'f'}]},  
{'selection_id': 1098, 'other_data': 89, 'value_dict':  
[{'value': '98', 'value_name': 'd'}, {'value': '4', 'value_name': 'r'}]}]

为避免疑问,对于任何给定的“ selection_id”,“ other_data”将始终相同,即,如果有两个“ selection_id” = 1099的实例,则“ other_data”将始终等于89(在示例中)它们都是89,但实际上对于不同的selection_id来说可能有所不同。

1 个答案:

答案 0 :(得分:1)

这是一种方法。

例如:

market=[{'selection_id': 1099,'value':'11', 'value_name': 'a', 'other_data': 89},  
{'selection_id': 1099,'value':'78', 'value_name': 'p', 'other_data': 89},  
{'selection_id': 1097,'value':'39', 'value_name': 'b', 'other_data': 89},  
{'selection_id': 1097,'value':'52', 'value_name': 'f', 'other_data': 89},  
{'selection_id': 1098,'value':'98', 'value_name': 'd', 'other_data': 89},  
{'selection_id': 1099,'value':'13', 'value_name': 'y', 'other_data': 89},  
{'selection_id': 1098,'value':'4', 'value_name': 'r', 'other_data': 89},
]

result = {}
for i in market:
    if i["selection_id"] not in result:
        result[i["selection_id"]] = {'selection_id': i["selection_id"], 'other_data': i["other_data"], 'value_dict': []}
    result[i["selection_id"]]["value_dict"].append({'value': i["value"], "value_name": i["value_name"]})


print(list(result.values()))

输出:

[{'other_data': 89,
  'selection_id': 1097,
  'value_dict': [{'value': '39', 'value_name': 'b'},
                 {'value': '52', 'value_name': 'f'}]},
 {'other_data': 89,
  'selection_id': 1098,
  'value_dict': [{'value': '98', 'value_name': 'd'},
                 {'value': '4', 'value_name': 'r'}]},
 {'other_data': 89,
  'selection_id': 1099,
  'value_dict': [{'value': '11', 'value_name': 'a'},
                 {'value': '78', 'value_name': 'p'},
                 {'value': '13', 'value_name': 'y'}]}]