简体   繁体   English

如何遍历所有嵌套字典以给出所有连接的父键及其值

[英]How to loop through all nested dictionary to give all the parent key concatenated and its value

dictionary={' items': { 'heading': 'Maps','description':'Maps123','imagepath':/music/images/','config':{'config1':12,'config2':123}},'db':{'username':'xyz','password':'xyz'},'version':'v1'}

I want the output in the format:我想要 output 的格式:

items/heading: Maps

items/description: Maps123

items/image_path: /music/images/v2/web_api-music.png

items/config/config1: abcd

items/config/config2: hello

db/username: xyz

db/password: xyz

version: v1

Check it:核实:

def flatten(x, parent=''):
    for key in list(x.keys()):
        if( type(x[key]) is dict ):
            flatten(x[key], parent+'/'+str(key))
        else:
            print(parent+'/'+str(key)+': ' + str(x[key]))

dictionary={'items': { 'heading': 'Maps','description':'Maps123','imagepath':'/music/images/','config':{'config1':12,'config2':123}},'db':{'username':'xyz','password':'xyz'},'version':'v1'}

flatten(dictionary)

The answer of script0 results in an output that starts with a forward slash ( / ). script0 的答案导致 output 以正斜杠 ( / ) 开头。 I modified script0's code a little:我稍微修改了script0的代码:

def flatten(x, parent=''):
    for key in x.keys():
        if isinstance(x[key], dict) and parent == '': flatten(x[key], key)
        elif isinstance(x[key], dict) and parent != '': flatten(x[key], f"{parent}/{key}")
        elif not isinstance(x[key], dict) and parent == '': print(f"{key}: {x[key]}")
        else: print(f"{parent}/{key}: {x[key]}")

dictionary= {'items': { 'heading': 'Maps','description':'Maps123','imagepath':'/music/images/','config':{'config1':12,'config2':123}},'db':{'username':'xyz','password':'xyz'},'version':'v1'}

flatten(dictionary)

Output (without the leading /): Output(没有前导/):

items/heading: Maps
items/description: Maps123
items/imagepath: /music/images/
items/config/config1: 12
items/config/config2: 123
db/username: xyz
db/password: xyz
version: v1

Please note that you could also create a new dictionary with the left-hand side of the output as the keys and the right-hand side as the values.请注意,您还可以创建一个新字典,将 output 的左侧作为键,将右侧作为值。

For example:例如:

new_dict = {}

def flatten(x, parent=''):
    for key in x.keys():
        if isinstance(x[key], dict) and parent == '': flatten(x[key], key)
        elif isinstance(x[key], dict) and parent != '': flatten(x[key], f"{parent}/{key}")
        elif not isinstance(x[key], dict) and parent == '': new_dict[key] = x[key]
        else: new_dict[f"{parent}/{key}"] = x[key]

dictionary= {'items': { 'heading': 'Maps','description':'Maps123','imagepath':'/music/images/','config':{'config1':12,'config2':123}},'db':{'username':'xyz','password':'xyz'},'version':'v1'}

flatten(dictionary)
print(new_dict)

Output: Output:

{'items/heading': 'Maps', 'items/description': 'Maps123', 'items/imagepath': '/music/images/', 'items/config/config1': 12, 'items/config/config2': 123, 'db/username': 'xyz', 'db/password': 'xyz', 'version': 'v1'}

A recursive function is best for this.递归 function 最适合这个。 It only needs to check the type of the parameter and pass down a path of keys:它只需要检查参数的类型并传递一个键的路径:

def paths(D,P=[]):
    if isinstance(D,dict):
        return {p:v for k,d in D.items() for p,v in paths(d,P+[k]).items()} 
    else:
        return {"/".join(P):D}

Output: Output:

print(paths(dictionary))

{'items/heading': 'Maps',
 'items/description': 'Maps123',
 'items/imagepath': '/music/images/',
 'items/config/config1': 12,
 'items/config/config2': 123,
 'db/username': 'xyz',
 'db/password': 'xyz',
 'version': 'v1'}

To make this a bit more efficient, you could make the function a generator and only create a dictionary from the extracted tuples at the end.为了提高效率,您可以将 function 设为生成器,最后仅从提取的元组中创建字典。

def paths(D,P=[]):
    if isinstance(D,dict):
        yield from ((p,v) for k,d in D.items() for p,v in paths(d,P+[k])) 
    else:
        yield ("/".join(P),D)
                        
dictionary = dict(paths(dictionary))

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM