30

Given a dictionary that looks like this:

{
    'Color': ['Red', 'Yellow'],
    'Size': ['Small', 'Medium', 'Large']
}

How can I create a list of dictionaries that combines the various values of the first dictionary's keys? What I want is:

[
    {'Color': 'Red', 'Size': 'Small'},
    {'Color': 'Red', 'Size': 'Medium'},
    {'Color': 'Red', 'Size': 'Large'},
    {'Color': 'Yellow', 'Size': 'Small'},
    {'Color': 'Yellow', 'Size': 'Medium'},
    {'Color': 'Yellow', 'Size': 'Large'}
]
Karl Knechtel
  • 62,466
  • 11
  • 102
  • 153
user1272534
  • 991
  • 2
  • 11
  • 17

2 Answers2

49

I think you want the Cartesian product, not a permutation, in which case itertools.product can help:

>>> from itertools import product
>>> d = {'Color': ['Red', 'Yellow'], 'Size': ['Small', 'Medium', 'Large']}
>>> [dict(zip(d, v)) for v in product(*d.values())]
[{'Color': 'Red', 'Size': 'Small'}, {'Color': 'Red', 'Size': 'Medium'}, {'Color': 'Red', 'Size': 'Large'}, {'Color': 'Yellow', 'Size': 'Small'}, {'Color': 'Yellow', 'Size': 'Medium'}, {'Color': 'Yellow', 'Size': 'Large'}]
Cristian Ciupitu
  • 20,270
  • 7
  • 50
  • 76
DSM
  • 342,061
  • 65
  • 592
  • 494
  • 2
    +1. Good to know that Python iterates over the dictionary items in the same, reproducible order, both for the `zip()` and the `.values()`! – Tim Pietzcker Mar 04 '13 at 21:59
  • 3
    @TimPietzcker: yes, this property is [documented](http://docs.python.org/2/library/stdtypes.html#dict.items) and can be relied on. The order itself is arbitrary, but no compliant Python implementation can violate the guarantee that if you don't modify `d`, `d.keys()` (here `d`) and `d.values()` have to match. – DSM Mar 04 '13 at 22:04
  • Thanks! This is perfect. – idnavid Jul 18 '19 at 22:34
  • I think since python 3.7 the dict order is also not arbitrary anymore! See also [here](https://stackoverflow.com/questions/50872498/will-ordereddict-become-redundant-in-python-3-7) – Marti Nito Jun 07 '21 at 16:09
1

You can obtain that result doing this:

x={'Color': ['Red', 'Yellow'], 'Size': ['Small', 'Medium', 'Large']}
keys=x.keys()
values=x.values()

matrix=[]
for i in range(len(keys)):
     cur_list=[]
     for j in range(len(values[i])):
             cur_list.append({keys[i]: values[i][j]})
     matrix.append(cur_list)

y=[]
for i in matrix[0]:
     for j in matrix[1]:
             y.append(dict(i.items() + j.items()))

print y

result:

[{'Color': 'Red', 'Size': 'Small'}, {'Color': 'Red', 'Size': 'Medium'}, {'Color': 'Red', 'Size': 'Large'}, {'Color': 'Yellow', 'Size': 'Small'}, {'Color': 'Yellow', 'Size': 'Medium'}, {'Color': 'Yellow', 'Size': 'Large'}]
sissi_luaty
  • 2,839
  • 21
  • 28