I got a df like this one:
level profile chest_gold chest_silver chest_bronze
1 a TRUE FALSE TRUE
2 a FALSE FALSE TRUE
3 a FALSE TRUE TRUE
I want to obtain a dictionary which uses as key the level and the profile to return something like this, converting the TRUE/FALSE in 1/0:
d[profile][level] = [1, 0, 1] #the chest result
for example:
d['a'][1] = [1,0,1]
d['a'][2] = [0,0,1]
d['a'][3] = [0,1,1]
How can I do that?
P.s. if you leave a solution please leave also a little comment to explain the answer!
CodePudding user response:
Check a nested dictionary comprehension. The inner comprehension builds dictionary where keys are levels and outer comprehension builds a dictionary where the keys are profiles.
output = {k: {i: v for i, *v in d.set_index('level').filter(like='chest').astype(int).to_records()} for k, d in df.groupby('profile')}
{'a': {1: [1, 0, 1], 2: [0, 0, 1], 3: [0, 1, 1]}}
CodePudding user response:
I think using itertuples()
to loop over rows would be more efficient. setdefault()
helps to build a nested dictionary by inserting a profile as key with an empty dictionary (which is filled in with level-chest values as the loop goes on)
# build a nested dictionary while iterating over rows of df
d = {}
for lvl, profile, *chest in df.mul(1).itertuples(index=False):
d.setdefault(profile, {})[lvl] = chest
d
# {'a': {1: [1, 0, 1], 2: [0, 0, 1], 3: [0, 1, 1]}}