需要在Python中将JSON重组为新结构。
例如:
{
'a' : 1,
'b' : 1,
'd' : {'d1' : '1', 'd2' : 2},
'm' : [
{'x' : 6, 'y' : 5, 'z' : {'foo' : 'foo1', 'bar' : 'bar1'} },
{'x' : 8, 'y' : 8, 'z' : {'foo' : 'foo2', 'bar' : 'bar2'} }
]
}
到
{
'new_a' : 1,
'new_d' : {'new_d1' : '1', 'new_d2' : 2},
'new_m' : [
{'new_x' : 6, 'new_z' : {'new_foo' : 'foo1', new_'bar : 'bar1'} },
{'new_x' : 8, 'new_z' : {'new_foo' : 'foo2', 'new_bar : 'bar2'} }
]
}
有一种旧形式的旧JSON
的想法有更优雅的方法吗?
import json
new_data = {}
new_data['new_a'] = old_data['a']
new_data['new_d'] = {}
new_data['new_d']['new_d1'] = old_data['d']['d1']
new_data['new_d']['new_d2'] = old_data['d']['d2']
new_data['new_m'] = {}
new_m = []
for m in old_data:
new_m.append({'new_x' : m['x'], 'new_z' : {'new_foo' ....
答案 0 :(得分:0)
您已经提到要求生成的代码必须删除“少数字段”。使用处理dicts和列表的递归循环,我们可以将所有键更改为new_
并删除您指定的任何字段。
a = {
'a' : 1,
'b' : 1,
'd' : {'d1' : '1', 'd2' : 2},
'm' : [
{'x' : 6, 'y' : 5, 'z' : {'foo' : 'foo1', 'bar' : 'bar1'} },
{'x' : 8, 'y' : 8, 'z' : {'foo' : 'foo2', 'bar' : 'bar2'} }
]
}
def rename(dt):
ndt = {}
for k, v in dt.iteritems():
if k == 'y': # the keys that you wish to remove from the new dictionary
continue
if isinstance(v, dict):
ndt['new_' + k] = rename(v)
elif isinstance(v, list):
ndt['new_' + k] = [rename(x) for x in v]
else:
ndt['new_' + k] = v
return ndt
print rename(a) # your expected dictionary
如果需要进行任何结构重组(例如,您想在其他地方移动值,或者如果您不想遵循您拥有的命名约定),那么您现有的代码已经是最干净的方法了如此。
答案 1 :(得分:0)
简单的递归解决方案将会:
def patch_keys(d, func):
"""
For a given dictionary `d`, recursively applies `func` to its keys,
filtering out those with `func(key)` evaluated to False.
For a list or tuple, applies `patch_keys` to each element.
Intended usage:
>>> patch_keys({1: 'a', 2: 'b'}, lambda x: x-1)
{1: 'b'}
"""
# we want to recursively apply self, i.e. `patch_keys(..., func=func)`
# here functools.partial comes in handy
self = partial(patch_keys, func=func)
if isinstance(d, dict):
# for a dict, apply self to values
return {func(k): self(v) for k, v in d.items() if func(k)}
elif isinstance(d, (list, tuple)):
# for list and tuples, apply self to each element
return type(d)(map(self, d))
else:
# else return as is
return copy.deepcopy(d)
结果:
>>> old_data = {
... 'a' : 1,
... 'b' : 1,
... 'd' : {'d1' : '1', 'd2' : 2},
... 'm' : [
... {'x' : 6, 'y' : 5, 'z' : {'foo' : 'foo1', 'bar' : 'bar1'} },
... {'x' : 8, 'y' : 8, 'z' : {'foo' : 'foo2', 'bar' : 'bar2'} }
... ]
... }
>>>
>>> patch_keys(old_data, new_keys)
{'new_d': {'new_d2': 2, 'new_d1': '1'}, 'new_m': [{'new_z': {'new_foo': 'foo1', 'new_bar': 'bar1'}}, {'new_z': {'new_foo': 'foo2', 'new_bar': 'bar2'}}], 'new_b': 1, 'new_a': 1}