Home > Net >  Creating Nested dictionary with multiple hierarchy separated with '.'
Creating Nested dictionary with multiple hierarchy separated with '.'

Time:07-18

I'm trying to create a multiple hierarchy of nested dictionary. The hierarchy levels are separated with a dot(.) in variable B however the final key (A) and value (D) are fixed.

Variables

A = "key"
B = "one.two.three.four"
D = "value"

Desired Output

{ one : { two : {three : {four : {key: value}}}}}

Here, the length of hierarchy (variable B) might increase or decrease based on input. I'm unable to create such dynamic code.

My pseudocode Code

A = "key"
B = "one.two.three.four"
D = "value"

inner_dictionary = {}
whole_dictionary = {}

lst = B.split('.')
length = len(lst)

for i in range(length):
    new = lst[-1]
    tmp = {A:D}
    inner_dictionary.update(tmp)
    val = { new : inner_dictionary}
    whole_dictionary.update(val)
    lst.pop()

print(whole_dictionary)

My Output

{'four': {'key': 'value'}, 'three': {'key': 'value'}, 'two': {'key': 'value'}, 'one': {'key': 'value'}}

I need help on this. Thanks in advance!

CodePudding user response:

Use this:

A = "key"
B = "one.two.three.four"
D = "value"

x = {A: D}

for k in B.split('.')[::-1]:
    x = {k: x}

print(x)

Output:

{'one': {'two': {'three': {'four': {'key': 'value'}}}}}

Or, in Python 3.8 , using the walrus operator:

A = "key"
B = "one.two.three.four"
D = "value"

x = {A: D}
[(x := {k: x}) for k in B.split('.')[::-1]]
print(x)

Output:

{'one': {'two': {'three': {'four': {'key': 'value'}}}}}

Note: the second solution takes a lot more time (you can run the following code to check that):

from timeit import timeit

print(timeit("""A = "key"
B = "one.two.three.four"
D = "value"
x = {A: D}
for k in B.split('.')[::-1]:
    x = {k: x}"""))

print(timeit("""A = "key"
B = "one.two.three.four"
D = "value"
x = {A: D}
[(x := {k: x}) for k in B.split('.')[::-1]]"""))

The first one takes about 0.5s, the second one about 1s.

CodePudding user response:

One approach using a single for-loop:

A = "key"
B = "one.two.three.four"
D = "value"


start = { A: D }
for k in reversed(B.split(".")):
    start = { k : start }
print(start)

Output

{'one': {'two': {'three': {'four': {'key': 'value'}}}}}

This type of problem where a list of values aggregates to a single one can be solved using reduce (a la functional programming):

from functools import reduce

A = "key"
B = "one.two.three.four"
D = "value"

res = reduce(lambda x, y: {y: x},  reversed(B.split(".")), {A: D})
  • Related