'How to dynamically populate a nested dictionary from another dictionary
I have a function that should convert it's input dictionaries into their correct format. Keys of each input dictionary contains one or more -> to indicate nested structure.
dict1 = {
'p1->a->b': 1,
'p1->a->c': 2,
'p1->d': 4,
'p2->a': 3
}
dict1_expected = {
'p1': {
'a': {
'b': 1,
'c': 2
},
'd': 4
},
'p2': {
'a': 3
}
}
def foo(input_dict):
# Process input_dict
return input dict
assert dict1_expected == foo(dict1)
Right now I can do this only one level deep in the following way:
dict1_expected = {}
for param in dict1:
if param.split("->")[0] not in dict1_expected:
dict1_expected.update({
param.split("->")[0]: {
param.split("->")[1]: dict1[param]
}
})
else:
dict1_expected[param.split("->")[0]].update({
param.split("->")[1]: dict1[param]
})
Solution 1:[1]
It's easier to make it using nested loop. Outer loop iterates over key-value pairs of dict1, inner loop iterate over splitted by -> key.
Code:
dict1 = {
'p1->a->b': 1,
'p1->a->c': 2,
'p1->d': 4,
'p2->a': 3,
'c': 0
}
dict1_expected = {}
for key, value in dict1.items():
current_dict = dict1_expected
*parts, last = key.split('->')
for part in parts:
if part not in current_dict:
current_dict[part] = {}
current_dict = current_dict[part]
current_dict[last] = value
Result:
{
'p1': {
'a': {
'b': 1,
'c': 2
},
'd': 4
},
'p2': {
'a': 3
},
'c': 0
}
You can help my country, check my profile info.
Solution 2:[2]
I came up with this:
def foo(input_dict):
# Process input_dict
res = {}
for path, value in input_dict.items():
curr = res
components = path.split('->')
for c in components[:-1]:
curr = curr.setdefault(c, {})
curr[components[-1]] = value
return res
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | |
| Solution 2 |
