Espoir Murhabazi
Espoir Murhabazi

Reputation: 6376

Get level of items in a nested list

Problem:

I have some linked data and I want to build a structure like this one on this picture :

my structure

and get the level of each item because in the future I will make some calculations by staring at the lowest level of my tree structure.

Expected Result:

I need to get a structure that gives me items per level :

what I have tried so far:

I've tried this recursive code to simulate the behavior but I'm unable to get items the level of items.

dict_item = {"A": ["B","C","D"], "D": ["E","F","G"], "E":["H","I","J"]}
def build_bom(product):
    if not dict_item.get(product):
        return product
    else :
        return [build_bom(x) for x in dict_item.get(product)]
print(build_bom("A"))

My output is a nested list like this :

['B', 'C', [['H', 'I', 'J'], 'F', 'G']]

My Question:

I'm not sure if this is the best approach to handle my problem. And how to get the desired output? here is the desired output :

[ {"parent_E":["H", "I", "J"]}, 
{"parent_D": ["E", "F", "G"]},
{"parent_A"} :["D","C","B"]},
]

A list of dictionaries ( where keys are parents and values are children), the first element in the list is the lowest level of my structure and the last is the highest element.

PS: This is a simulation but in future, I will have to works on large datasets with this code. Any Help will be appreciated

Upvotes: 0

Views: 2183

Answers (1)

codelessbugging
codelessbugging

Reputation: 2909

This is how I will approach this problem. First, I'll generate the tree from your dict_item object.

dict_item = {"A": ["B","C","D"], "D": ["E","F","G"], "E":["H","I","J"]}

def build_tree(x):
    if x in dict_item:
        return {x: [build_tree(v) for v in dict_item[x]]}
    else:
        return x

tree = build_tree("A")
print(tree)
>>> {'A': ['B', 'C', {'D': [{'E': ['H', 'I', 'J']}, 'F', 'G']}]}

Then, do a breadth-first search on the tree. Each time we hit an element that has children, we append it to a list:

results = []
queue = [tree]

while queue:
    x = queue.pop(0)
    if isinstance(x, dict):
        parent, children = list(x.items())[0]
        results.append({'parent_' + parent: dict_item[parent]})
        for child in children:
            queue.append(child)

print(results)
>>> [{'parent_A': ['B', 'C', 'D']}, {'parent_D': ['E', 'F', 'G']}, {'parent_E': ['H', 'I', 'J']}]

Then all we need to do now, is to reverse the list:

print list(reversed(results))
>>> [{'parent_E': ['H', 'I', 'J']}, {'parent_D': ['E', 'F', 'G']}, {'parent_A': ['B', 'C', 'D']}]

Upvotes: 1

Related Questions