简体   繁体   中英

Elegant way of finding unique string pairs from dictionary values in a list of dictionaries

I have a list of dictionaries:

    some_list = [
                  {
                     item1:'a', 
                     item2:['1', '2']
                  }, 
                  {
                     item1:'b', 
                     item2:['1', '2']
                  }, 
                  {
                     item1:'a', 
                     item2:['1']
                  }
                ]

I would like to get:

['a 1', 'a 2', 'b 1', 'b 2'] where each value from item 1 is paired with value from item 2 for each dictionary, and then only the unique strings are left.

I can think of an obvious way to do it, namely:

  1. iterate through the some_list;
  2. for each dictionary, get a each['item_1'] and each['item_2']
  3. for member of each['item_2'] do each['item_1'] + ' ' + member
  4. Now, make the list into a set and I have my unique values

I am wondering if these is a more elegant way to do it using list comprehension.

If order doesn't matter, then you can easily translate your logic into a set-comprehnsion (and convert to list if you'd like):

In [1]: some_list = [
   ...:                   {
   ...:                      'item1':'a',
   ...:                      'item2':['1', '2']
   ...:                   },
   ...:                   {
   ...:                      'item1':'b',
   ...:                      'item2':['1', '2']
   ...:                   },
   ...:                   {
   ...:                      'item1':'a',
   ...:                      'item2':['1']
   ...:                   }
   ...:                 ]

In [2]: {f"{d['item1']} {v}" for d in some_list for v in d['item2']}
Out[2]: {'a 1', 'a 2', 'b 1', 'b 2'}
def fun(item):
     return [item[item1]+' '+k for k in item[item2]]
res = []
[res.append(fun(i)) for i in some_list if(fun(i)) not in res]
print res

this should work

another formatting option, runs back to 2.7

sorted(map(' '.join,
           {(d['item1'], v)
            for d in some_list
                for v in d['item2']}))

still a 'one-liner' but with decorative line breaks and indentation

inner list comp same as other ans, arrived at independently without seeing it 1st

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM