如何用Python查找嵌套JSON中指定Key的完整路径?
递归查找嵌套JSON中指定Key的完整路径
问题需求
需要在嵌套JSON结构中,找出指定Key对应的所有完整路径及对应值。现有递归代码仅能提取值,无法记录路径,需修改实现路径追踪功能。
输入JSON
{ "id": ["0001"], "type": "donut", "name": "Cake", "ppu": 0.55, "batters": { "batter": { "id": ["1001"], "type": "Regular" } }, "topping": [ { "id": ["5001"], "type": "None" }, { "id": ["5002"], "type": "Glazed" } ] }
期望输出
[ {"id":["0001"]}, {"batters.batter.id":["1001"]}, {"topping[0].id":["5001"]}, {"topping[1].id":["5002"]} ]
注:原期望输出最后一项路径存在笔误,已修正为topping[1].id
现有代码(无法追踪路径)
def json_extract(obj, key): """Recursively fetch values from nested JSON.""" arr = [] def extract(obj, arr, key): """Recursively search for values of key in JSON tree.""" if isinstance(obj, dict): for k, v in obj.items(): if isinstance(v, (dict)): extract(v, arr, key) elif k == key: arr.append(v) elif isinstance(obj, list): for item in obj: extract(item, arr, key) return arr values = extract(obj, arr, key) return values
解决方案代码
修改递归逻辑,新增current_path参数追踪当前节点路径,遇到字典时拼接键名、遇到列表时拼接索引,找到目标Key时将完整路径与对应值组成字典存入结果:
def json_extract_with_path(obj, target_key): result = [] def extract_recursive(current_obj, current_path): if isinstance(current_obj, dict): for key, value in current_obj.items(): # 拼接字典节点的路径,根节点直接用键名,非根节点加.分隔 new_path = f"{current_path}.{key}" if current_path else key if key == target_key: result.append({new_path: value}) # 递归处理子节点 extract_recursive(value, new_path) elif isinstance(current_obj, list): for index, item in enumerate(current_obj): # 拼接列表节点的路径,用[index]标注索引 new_path = f"{current_path}[{index}]" if current_path else f"[{index}]" # 递归处理列表内的元素 extract_recursive(item, new_path) extract_recursive(obj, "") return result
代码说明
- 路径累积:通过
current_path参数在递归过程中实时记录当前节点的完整路径,初始值为空字符串。 - 字典节点处理:遍历字典键值对时,将当前键拼接到路径后,若当前键为目标Key,直接将路径-值字典加入结果列表。
- 列表节点处理:遍历列表元素时,将元素索引以
[index]格式拼接到路径后,继续递归处理列表内的嵌套结构。 - 调用示例:
运行后即可得到符合期望的输出结果。# 代入输入JSON调用函数 sample_json = { "id": ["0001"], "type": "donut", "name": "Cake", "ppu": 0.55, "batters": {"batter": {"id": ["1001"], "type": "Regular"}}, "topping": [{"id": ["5001"], "type": "None"}, {"id": ["5002"], "type": "Glazed"}] } print(json_extract_with_path(sample_json, "id"))
内容的提问来源于stack exchange,提问作者NAGA RAJ S
相关产品推荐
相关产品推荐

