I have a json object which is very deep. In other words I have a dictionary, containing dictionaries containing dictionaries and so on many times. So, one can imagine it as a huge tree in which some nodes are very far from the root node.
Now I would like to cut this tree so that I have in it only nodes that are separated not more than N steps from the root. Is there a simple way to do it?
For example if I have:
{'a':{'d':{'e':'f', 'l':'m'}}, 'b':'c', 'w':{'x':{'z':'y'}}}
And I want to keep only nodes that are 2 steps from the root, I should get:
{'a':{'d':'o1'}, 'b':'c', 'w':{'x':'o2'}}
So, I just replace the far standing dictionaries by single values.
Given that your data is very deep, you may very well run into stack limits with recursion. Here's an iterative approach that you might be able to clean up and polish a bit:
import collections
def cut(dict_, maxdepth, replaced_with=None):
"""Cuts the dictionary at the specified depth.
If maxdepth is n, then only n levels of keys are kept.
"""
queue = collections.deque([(dict_, 0)])
# invariant: every entry in the queue is a dictionary
while queue:
parent, depth = queue.popleft()
for key, child in parent.items():
if isinstance(child, dict):
if depth == maxdepth - 1:
parent[key] = replaced_with
else:
queue.append((child, depth+1))
def prune(tree, max, current=0):
for key, value in tree.items():
if isinstance(value, dict):
if current == max:
tree[key] = None
else:
prune(value, max, current + 1)
This is mostly an example to get you started. It prunes the dictionary in place. E.g.:
>>> dic = {'a':{'d':{'e':'f', 'l':'m'}}, 'b':'c', 'w':{'x':{'z':'y'}}}
>>> prune(dic, 1)
>>> dic
{'b': 'c', 'w': {'x': None}, 'a': {'d': None}}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With