'Increase efficency in list rearranging

I have a list of dictionaries like this:

[{'class': ['title is-5', 'company', 'location']}, 
{'class': ['subtitle is-3', 'title is-1']}]

The goal is to turn that into 2 separate lists like this:

[[{'class': 'title is-5'}, {'class': 'company'}, {'class': 'location'}], 
[{'class': 'subtitle is-3'}, {'class': 'title is-1'}]]

I wrote a function that accomplishes that:

def AggregateAttributes(config_attr: list):
    final_attr_list = []
    for list_attr in config_attr:
        attr_value_list = []
        for key, val in list_attr.items():
            for attr_val in val:
                attr_value_list.append({key: attr_val})
        final_attr_list.append(attr_value_list)
    return final_attr_list

Is there a way to do this without having to use 3 for loops?? I feel like this solution is super inefficient.



Solution 1:[1]

Python has a short hand syntax that allows you to compile some pretty complicated iterables (lists, dicts, etc.) in a single line.

This will do the trick for you:

dict_list = [{'class': ['title is-5', 'company', 'location']}, {'class': ['subtitle is-3', 'title is-1']}]

my_list = [[{'class':v} for v in dict_list[i]['class']] for i in range(len(dict_list))]

print(my_list)

As a simpler example, I cam make a list of 1200 integers from 0 to 1199 like this:

my_list = [i for i in range(0, 1200)]

within this line I have the flexibility to make edits before the final list is created. Let's say I wanted integer values to be the chr() representations.

my_list = [chr(i) for i in range(100)]

or strings...

my_list = [str(i) for i in range(100)]

The last one is identical to this:

my_list = []
for i in range(100):
    my_list.append(str(i))

Solution 2:[2]

Apparently, your code is already efficient. Just make it into list comprehension and it will be faster.

[[{key: attr_val} for attr_val in val] for list_attr in a for key,val in list_attr.items() ]

%timeit [[{key: attr_val} for attr_val in val] for list_attr in a for key,val in list_attr.items() ]

1.87 µs ± 85.4 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

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