Search keys and read from multiple dictionaries

Question:

Several dictionaries containing different keys and values.

By looping a list of keys, I want to return their values in the dictionaries (when the key is available), and sum them.

The problem is, some keys are not available in all the dictionaries.

I need to come up with different IF statements, which look clumsy. Especially when there are more dictionaries came in, it became very difficult.

What is the different smart way to do so?

dict_1 = {"Mike": 1, "Lilly": 2, "David": 3}
dict_2 = {"Mike": 4, "Peter": 5, "Kate": 6}
dict_3 = {"Mike": 7, "Lilly": 8, "Jack": 9}

for each in ["Mike", "Lilly", "David"]:
    if each in list(dict_1.keys()) and each in list(dict_2.keys()) and each in list(dict_3.keys()):
        print (each, dict_1[each] * 1 + dict_2[each] * 2 + dict_3[each] * 3)
    if each in list(dict_1.keys()) and each in list(dict_2.keys()):
        print (each, dict_1[each] * 1 + dict_2[each] * 2)
    if each in list(dict_2.keys()) and each in list(dict_3.keys()):
        print (dict_2[each] * 2 + dict_3[each] * 3)
    if each in list(dict_1.keys()) and each in list(dict_3.keys()):
        print (each, dict_1[each] * 1 + dict_3[each] * 3)
Asked By: Mark K

||

Answers:

You can pass 0 if the key is not found.

for each in ["Mike", "Lilly", "David"]:
    print(each, dict_1.get(each, 0)*1 + dict_2.get(each, 0)*2 + dict_3.get(each, 0)*3)

Output:

Mike 30
Lilly 26
David 3
Answered By: Ash Nazg

Since the dicts are named with sequential numbers, a more streamlined approach would be to put them in a list and use enumerate to generate the factors that you apply to the values in each dict when you sum them by key:

records = [
    {"Mike": 1, "Lilly": 2, "David": 3},
    {"Mike": 4, "Peter": 5, "Kate": 6},
    {"Mike": 7, "Lilly": 8, "Jack": 9}
]

for name in "Mike", "Lilly", "David":
    print(name, sum(factor * record.get(name, 0) for factor, record in enumerate(records, 1)))

This outputs:

Mike 30
Lilly 26
David 3
Answered By: blhsing

(Given that you are checking the sum of total occurances of elements in different dictictionaries) I do think collections.Counter is a better way of doing your task:
https://docs.python.org/3/library/collections.html#collections.Counter

Examples

from collections import Counter
counter1 = Counter({"Mike": 1, "Lilly": 2, "David": 3}) #counter object from a mapping
counter2 = Counter({"Mike": 4, "Peter": 5, "Kate": 6})
counter3 = Counter({"Mike": 7, "Lilly": 8, "Jack": 9})

countertotal = counter1+counter2+counter2+counter3+counter3+counter3
>>>countertotal

Counter({'Mike': 30,
         'Lilly': 26,
         'David': 3,
         'Peter': 10,
         'Kate': 12,
         'Jack': 27})

Count of element occurrences can be directly assessed:

for each in ["Mike", "Lilly", "David"]:
  print(countertotal[each])

30
26
3

Checking the existence of elements do not throw an error:

for each in ["Ada", "Albert", "Adrian"]:
  print(countertotal[each])

0
0
0
Answered By: adrianop01

You can check if key is in dictionary before you attempt to access it.

dict_list = [
        {"Mike": 1, "Lilly": 2, "David": 3},
        {"Mike": 4, "Peter": 5, "Kate": 6},
        {"Mike": 7, "Lilly": 8, "Jack": 9},
    ]

    dict_res = {"Mike": 0, "Lilly": 0, "David": 0}

    #loop through each of the names you want
    for key in dict_res.items():
        x = 1

        #loop through each of your dictionaries
        for dict in dict_list:
            if key in dict:
                # multiply by dictionary number and add to result value
                dict_res[key] += dict[key] * x
            x += 1
    print(dict_res)

Output:  {'Mike': 30, 'Lilly': 26, 'David': 3}
Answered By: polarmolar