我有很多json文件,它们的结构是不同的。我每次都需要更改json中一个字段的值,其他字段的值保持不变。
现在,我已经能够动态地获得json的路径代码,如下所示
def get_paths(source):
paths = []
if isinstance(source, collections.MutableMapping): # found a dict-like structure...
for k, v in source.items(): # iterate over it; Python 2.x: source.iteritems()
paths.append([k]) # add the current child path
paths += [[k] + x for x in get_paths(v)] # get sub-paths, extend with the current
# else, check if a list-like structure, remove if you don't want list paths included
elif isinstance(source, collections.Sequence) and not isinstance(source, str):
for i, v in enumerate(source):
paths.append([i])
paths += [[i] + x for x in get_paths(v)] # get sub-paths, extend with the current
return paths其中一个json示例如下,它只是众多json中的一个:
{
"glossary": {
"title": "example glossary",
"GlossDiv": {
"title": "S",
"GlossList": {
"GlossEntry": {
"ID": "SGML",
"SortAs": "SGML",
"GlossTerm": "Standard Generalized Markup Language",
"Acronym": "SGML",
"Abbrev": "ISO 8879:1986",
"GlossDef": {
"para": "A meta-markup language, used to create markup languages...",
"GlossSeeAlso": [
"GML",
"XML"
]
},
"GlossSee": "markup"
}
}
}
}
}使用以下代码获取路径
def loadJson():
try:
with open('../json/test1.json', 'r') as loadf:
load_dict = json.load(loadf)
return load_dict
except Exception as e:
raise Exception("load json fail")
t_json = loadJson()
paths = get_paths(loadJson())此示例中的路径如下:
[['glossary'],
['glossary', 'title'],
['glossary', 'GlossDiv'],
['glossary', 'GlossDiv', 'title'],
['glossary', 'GlossDiv', 'GlossList'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'ID'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'SortAs'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossTerm'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'Acronym'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'Abbrev'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossDef'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossDef', 'para'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossDef', 'GlossSeeAlso'],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossDef', 'GlossSeeAlso', 0],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossDef', 'GlossSeeAlso', 1],
['glossary', 'GlossDiv', 'GlossList', 'GlossEntry', 'GlossSee']]现在的问题是如何通过获取的路径动态修改其中一个字段的值?
示例:我想将"title": "S"修改为"title": "M"。
如何使用['glossary', 'GlossDiv', 'title']做到这一点呢?
for path in paths:
# How to get t_json[path[0]][path[1]][path[2]]?发布于 2019-06-14 08:41:31
如何获取
t_json[path[0]][path[1]][path[2]]?
简单:我们只需要遍历path,一次应用一个索引操作。这要求我们在每一步之后记住我们的进度,最简单的方法是重用一个在整个路径中跟踪其路径的变量。因此,例如:
element = t_json
for path_item in path:
element = element[path_item]发布于 2019-06-14 09:36:02
下面是如何使用path的基本思想,它是一个键序列:
from functools import reduce
# From https://stackoverflow.com/a/28225747/355230
def recursive_get(d, *keys):
return reduce(lambda c, k: c.get(k, {}), keys, d)
t_json = loadJson()
path = ['glossary', 'GlossDiv', 'title']
sub_dict = recursive_get(t_json, *path[:-1])
sub_dict['title'] = 'M'
print(t_json)https://stackoverflow.com/questions/56589613
复制相似问题