howhow
howhow

Reputation: 103

Separate dictionary into multiple lists using values

I've got a function that I use to populate a dictionary. The function iterates over two layers in QGIS and returns the attributes where the layers intersect and assigns the keys and values to the dict as below:

dict[id_code] = value

The contents of the dictionary :

{'CB000004657321': 'LT_07324_TRN1', 'CB000004657327': 'LT_07324_TRN1', 'CB000004132360': 'LT_07324_TRN2', 'CB000004132384': 'LT_07324_TRN2', 'CB000004133606': 'LT_07324_TRN2', 'CB000004133629': 'LT_07324_TRN2', 'CB000004131653': 'LT_07324_TRN2', 'CB000004130408': 'LT_07324_TRN2', 'CB000004132025': 'LT_07324_TRN2', 'CB000004131107': 'LT_07324_TRN2', 'CB000004130785': 'LT_07324_TRN2', 'CB000004132780': 'LT_07324_TRN2', 'CB000004130778': 'LT_07324_TRN2', 'CB000004132018': 'LT_07324_TRN2', 'CB000004658296': 'LT_07324_TRN1', 'CB000004657328': 'LT_07324_TRN1'}

The function works fine, and dictionary contains all the key-pairs as expected. In the dict there are around 15 key-values pairs. For now i'm testing with 2 possible values. What I'd like to do is separate my dictionary based on the values (split into two lists) - i.e. list_1 = ([key + vals]) where vals == 'type_a' / list_2 = ([key + vals]) where vals == 'type_b' etc

What I've tried so far is:

  1. I get a set of the unique values in my dictionary with :s_vals = set(dict.values()) which i use in the loop below.

    I'm using s_val and not just values hard coded because these can change between projects (hence i make a set unique values first)

  2. I create 2 empty list :

    list_1 = []
    list_2 = []
    
  3. I then use the function below to populate my lists:

    def fn_ouput_list(liste, dict):
        for elem in s_vals:
            for key, value in dict.items():
                if dict[key][:] == elem:
                    liste.extend([key, value])
        return liste
    
    list_1 = fn_ouput_list(list_1, dict) 
    list_2 = fn_ouput_list(list_2, dict)
    

The problem is my function produces two identical lists, with all the key-values pairs, and I don't really understand why?

I was trying to split the dictionary into two list, but might two dictionaries be better/easier?

Upvotes: 0

Views: 623

Answers (1)

stevemo
stevemo

Reputation: 1097

If I understand you correctly, you could iterate over the dict and just build the two lists as you go,

d = {'a': '000_TRN1', 'b': '000_TRN2'}

list1 = []
list2 = []
for k,v in d.items():
    if v[-1] == '1':   # if last letter of value is '1'
        list1.append((k,v))
    elif v[-1] == '2': # if last letter of value is '2'
        list2.append((k,v))

print(list1)
# [('a', '000_TRN1')]

print(list2)
# [('b', '000_TRN2')] 

or, a little more concise but does extra work,

list1 = [(k,v) for k,v in d.items() if v[-1]=='1']
list2 = [(k,v) for k,v in d.items() if v[-1]=='2']

EDIT: Based on OP's comment, consider building the lists in a dict, to save on if/else statements,

d = {'CB000004132018': 'LT_07324_TRN2', 'CB000004658296': 'LT_07324_TRN1'}

z = {v[-4:]: [] for v in d.values()}
for k,v in d.items():
    z[v[-4:]].append((k,v))

z
# {'TRN1': [('CB000004658296', 'LT_07324_TRN1')],
#  'TRN2': [('CB000004132018', 'LT_07324_TRN2')]}

and you could pull the lists out however you want, or do

alllists = [v for v in z.values()]

and get a list of lists.

Upvotes: 1

Related Questions