Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to create a list of dictionaries from a dictionary with lists of different lengths

I want to create a list of dictionaries with the same index element from each list.

I have this dictionary:

d = {'name': ['bob', 'john', 'harry', 'mary'],       'age': [13, 19, 23],       'height': [164, 188],       'job': ['programmer']} 

The desired output is:

d2 = [{'name': 'bob', 'age': 13, 'height': 164, 'job': 'programmer'},        {'name': 'john', 'age': 19, 'height': 188},        {'name': 'harry', 'age': 23},       {'name': 'mary'}] 

I have tried something like this:

d2 = [dict(zip(d, t)) for t in zip(*d.values())] 

But my output is:

d2 = [{'name': 'bob', 'age': 13, 'height': 164, 'job': 'programmer'}] 

I think this is happening because the lists have different lengths.

like image 556
raul Avatar asked Sep 09 '19 09:09

raul


People also ask

How do I create a multi list in a dictionary?

By using zip() and dict() method The zip() method takes multiple iterable objects as arguments such as lists and tuples and returns an iterator. In Python, the dict() method creates an empty dictionary. In this example, the dict and zip() method join together to convert lists into dictionaries.

How do I sort a list of dictionaries by a value of the dictionary?

To sort a list of dictionaries according to the value of the specific key, specify the key parameter of the sort() method or the sorted() function. By specifying a function to be applied to each element of the list, it is sorted according to the result of that function.

How do you get a list of all the values in a dictionary?

In Python to get all values from a dictionary, we can use the values() method. The values() method is a built-in function in Python and returns a view object that represents a list of dictionaries that contains all the values.


2 Answers

You can use itertools.zip_longest and filter out None values:

from itertools import zip_longest  [{x: y for x, y in zip(d, t) if y is not None} for t in zip_longest(*d.values())] # [{'name': 'bob', 'age': 13, 'height': 164, 'job': 'programmer'},  #  {'name': 'john', 'age': 19, 'height': 188},  #  {'name': 'harry', 'age': 23},  #  {'name': 'mary'}] 
like image 81
user2390182 Avatar answered Sep 23 '22 23:09

user2390182


You can use zip_longest here:

from itertools import zip_longest  keys = d.keys()  d2 = [     {k: v for k, v in zip(keys, vs) if v is not None}     for vs in zip_longest(*d.values()) ]

If the values can be None as well, we can circumvent that by using a dummy value:

from itertools import zip_longest  keys = d.keys() dummy = object()  d2 = [     {k: v for k, v in zip(keys, vs) if v is not dummy}     for vs in zip_longest(*d.values(), fillvalue=dummy) ]

Here the dummy is an object which we are sure that is not part of the items in d (since we construct it after we constructed d). By using an is comparison, we thus can know if that value was the "fillvalue".

This will give us:

>>> d2 [{'name': 'bob', 'age': 13, 'height': 164, 'job': 'programmer'}, {'name': 'john', 'age': 19, 'height': 188}, {'name': 'harry', 'age': 23}, {'name': 'mary'}] 
like image 39
Willem Van Onsem Avatar answered Sep 21 '22 23:09

Willem Van Onsem