Home > Enterprise >  How to find common key value pairs from within nested dictionaries
How to find common key value pairs from within nested dictionaries

Time:03-24

I have this nested dictionary

Movies = {1: {'1060277': 'cloverfield', '1877830': 'The Batman', '0117283': 'The Pallbearer'},
          2: {'1877830': 'The Batman', '1877321': 'The Yards', '0117283': 'The Pallbearer'},
          3: {'6723592': 'Tenet', '1099212': 'Twilight', '1877830': 'The Batman'}}

Now i want to return a dictionary that has the common key value pairs from all the dictionaries within the nested dictionary, in this case it would be

--> 1877830 The Batman

As its the only one that's common in all 3 nested dictionaries

What i cant seem to figure out how to compare these dictionaries

#mov is where Movies will be passed    
def Narrow_down(mov):
      final_list= mov[1]
      for i in final_list.keys():
        for x,y in mov.items(): 
            for key in y:
                if i==key:
                    print(i, "is common ")

CodePudding user response:

You basically want to take the first dictionary, and then for every next dictionary, only keep the keys from the first that are also in the next.

A very straightforward solution uses functools.reduce():

from functools import reduce

# you don't really need the outer dictionary, but if you do, this is list(Movies.keys())
movies = [
    {'1060277': 'cloverfield', '1877830': 'The Batman', '0117283': 'The Pallbearer'},
    {'1877830': 'The Batman', '1877321': 'The Yards', '0117283': 'The Pallbearer'},
    {'6723592': 'Tenet', '1099212': 'Twilight', '1877830': 'The Batman'}
]

result = reduce(lambda d1, d2: {k: v for k, v in d1.items() if k in d2 and d2[k] == d1[k]}, movies)

print(result)

Result:

{'1877830': 'The Batman'}

Note that I named the variable movies - you should avoid naming variables with capitals, as that will cause others (and perhaps future you) to assume it's a class name.

CodePudding user response:

You can iterate over the values of the outer dictionary, maintaining a set of key-value pairs that are common to all the dictionaries seen so far (using the set intersection operation). You can then translate this set of key-value pairs into a dictionary using a dictionary comprehension:

common_items = None

for inner_dict in Movies.values():
    if common_items is None:
        common_items = set(inner_dict.items())
    else:
        common_items = common_items.intersection(inner_dict.items())

result = {key: value for key, value in common_items}
print(result)

With the given movies, this prints:

{'1877830': 'The Batman'}

CodePudding user response:

You can use a set intersection of the dictionaries items:

set.intersection(*(set(d.items()) for d in Movies.values()))

Output: {('1877830', 'The Batman')}

As dictionary:

dict(set.intersection(*(set(d.items()) for d in Movies.values())))

Output: {'1877830': 'The Batman'}

CodePudding user response:

If you really only want the common key-value pairs, then here is code that removes the key-value pairs that have the same key but different values for this key:

common_keys: set = None

for _, nested_dict in Movies.items():
    if common_keys is None:
        common_keys = set(nested_dict.keys())
    else:
        common_keys = common_keys.intersection(set(nested_dict.keys()))


# remove key-value pairs with same keys but different values
common_key_value_pairs = {}
common_keys_different_values = set()

for common_key in common_keys:
    for _, nested_dict in Movies.items():
        if common_key in common_key_value_pairs:
            if common_key_value_pairs[common_key] != nested_dict[common_key]:
                common_keys_different_values.add(common_key)
        else:
            common_key_value_pairs[common_key] = nested_dict[common_key]

for key in common_keys_different_values:
    print(f"Key {key} has different values in the respective dicts")
    del common_key_value_pairs[key]
    
print(common_key_value_pairs)
  • Related