Merge dictionaries with minimum value of common keys - python

I have two dictionaries. I want to merge these dictionaries such that the value for any key in the resultant dictionary is the minimum of the values for the key in the two dictionaries used to merge.
h1 = {"a":3, "b":5, "c":2}
h2 = {"a":1, "c":5, "d":10}
result = merge(h1, h2) = {"a":1, "b":5, "c":2, "d":10}
Is there a cool one liner do so? If not, what is the most elegant way of doing this?

You can do it like this
>>> {k: min(i for i in (h1.get(k), h2.get(k)) if i) for k in h1.viewkeys() | h2}
{'a': 1, 'c': 2, 'b': 5, 'd': 10}
h1.viewkeys() | h2 actually finds the set union and gets all the keys which are either in h1 or h2. Then, we find the minimum value of the corresponding key from h1 and `h2.
If you are using Python 3.x, then you just need to use keys, like this
>>> {k : min(i for i in (h1.get(k), h2.get(k)) if i is not None) for k in h1.keys() | h2}
{'d': 10, 'a': 1, 'b': 5, 'c': 2}
Note: The above shown set like operations are working, because they really are set-like. Quoting the official documentation,
Keys views are set-like since their entries are unique and hashable. If all values are hashable, so that (key, value) pairs are unique and hashable, then the items view is also set-like. (Values views are not treated as set-like since the entries are generally not unique.)

You can try this too:
>>> {k: min(h1.get(k) or h2[k], h2.get(k) or h1[k]) for k in (h1.keys() + h2.keys())}
{'a': 1, 'c': 2, 'b': 5, 'd': 10}

Related

Get value of dictionaries into separate lists

I am trying to get array by first key.
The names of the keys are always the same and the number of elements is the same.
[{'a': 1, 'b':41, 'c':324}, {'a': 1, 'b':12, 'c':65}, {'a': 2, 'b':36, 'c':12}]
expected output:
[{'b':41, 'c':324}, {'b':12, 'c':65}]
[{'b':36, 'c':12}]
Make a new dictionary that uses the values of the a keys as its keys.
newdict = {}
for d in data:
newdict.setdefault(d['a'], []).append({'b': d['b'], 'c': d['c']})
result = list(new_dict.values())

How to create a dict out of 2 dict's that already exist in Python 3

How can I create a new dictionary out of 2 dictionaries that I already have created?
It should look like this:
d1 = {'a': 2, 'b': 3}
d2 = {'s': 4, 'k': 5}
The keys from d1 and the values from d2 have to be in d3.
d3= {'a': 4, 'b': 5}
Is there an operation that combines the keys from one dict and the values from another dict to create a new dictionary.
It can be done several ways. If you wish to use a loop you try this:
for i in range(len(d1.keys())):
d1[d1.keys()[i]]=d2.values()[i]
Make sure the structure remains same of both the dictionaries.
Dictionaries do not have ordering, then u can use OrderedDict or tuple and zip for union.
Example
from collections import OrderedDict
d1 = {'a': 2, 'b':3}
d2 = {'s': 4, 'k': 5}
d1 = OrderedDict(d1)
d2 = OrderedDict(d2)
for value_d1,value_d2 in zip(d1.values(),d2.values()):
new_value = value_d1 + value_d2
Since you were not very specific in your problem, I have no way of trying to show something more elegant.
d1={'a':2,'b':3}
d2={'s':4,'k':5}
k=list(d1.keys())
v=list(d2.values())
d3={}
for i in range(len(k)):
d3[k[i]]=v[i]
Use check before the loop to make sure that number of keys equals number of values to avoid getting exceptions.

Getting the difference (in values) between two dictionaries in python

Let's say you are given 2 dictionaries, A and B with keys that can be the same but values (integers) that will be different. How can you compare the 2 dictionaries so that if the key matches you get the difference (eg if x is the value from key "A" and y is the value from key "B" then result should be x-y) between the 2 dictionaries as a result (preferably as a new dictionary).
Ideally you'd also be able to compare the gain in percent (how much the values changed percentage-wise between the 2 dictionaries which are snapshots of numbers at a specific time).
Given two dictionaries, A and B which may/may not have the same keys, you can do this:
A = {'a':5, 't':4, 'd':2}
B = {'s':11, 'a':4, 'd': 0}
C = {x: A[x] - B[x] for x in A if x in B}
Which only subtracts the keys that are the same in both dictionaries.
You could use a dict comprehension to loop through the keys, then subtract the corresponding values from each original dict.
>>> a = {'a': 5, 'b': 3, 'c': 12}
>>> b = {'a': 1, 'b': 7, 'c': 19}
>>> {k: b[k] - a[k] for k in a}
{'a': -4, 'b': 4, 'c': 7}
This assumes both dict have the exact same keys. Otherwise you'd have to think about what behavior you expect if there are keys in one dict but not the other (maybe some default value?)
Otherwise if you want to evaluate only shared keys, you can use the set intersection of the keys
>>> {k: b[k] - a[k] for k in a.keys() & b.keys()}
{'a': -4, 'b': 4, 'c': 7}
def difference_dict(Dict_A, Dict_B):
output_dict = {}
for key in Dict_A.keys():
if key in Dict_B.keys():
output_dict[key] = abs(Dict_A[key] - Dict_B[key])
return output_dict
>>> Dict_A = {'a': 4, 'b': 3, 'c':7}
>>> Dict_B = {'a': 3, 'c': 23, 'd': 2}
>>> Diff = difference_dict(Dict_A, Dict_B)
>>> Diff
{'a': 1, 'c': 16}
If you wanted to fit that all onto one line, it would be...
def difference_dict(Dict_A, Dict_B):
output_dict = {key: abs(Dict_A[key] - Dict_B[key]) for key in Dict_A.keys() if key in Dict_B.keys()}
return output_dict
If you want to get the difference of similar keys into a new dictionary, you could do something like the following:
new_dict={}
for key in A:
if key in B:
new_dict[key] = A[key] - B[key]
...which we can fit into one line
new_dict = { key : A[key] - B[key] for key in A if key in B }
here is a python package for this case:
https://dictdiffer.readthedocs.io/en/latest/
from dictdiffer import diff
print(list(diff(a, b)))
would do the trick.

Removing dictionaries from a list on the basis of duplicate value of key

I am new to Python. Suppose i have the following list of dictionaries:
mydictList= [{'a':1,'b':2,'c':3},{'a':2,'b':2,'c':4},{'a':2,'b':3,'c':4}]
From the above list, i want to remove dictionaries with same value of key b. So the resultant list should be:
mydictList = [{'a':1,'b':2,'c':3},{'a':2,'b':3,'c':4}]
You can create a new dictionary based on the value of b, iterating the mydictList backwards (since you want to retain the first value of b), and get only the values in the dictionary, like this
>>> {item['b'] : item for item in reversed(mydictList)}.values()
[{'a': 1, 'c': 3, 'b': 2}, {'a': 2, 'c': 4, 'b': 3}]
If you are using Python 3.x, you might want to use list function over the dictionary values, like this
>>> list({item['b'] : item for item in reversed(mydictList)}.values())
Note: This solution may not maintain the order of the dictionaries.
First, sort the list by b-values (Python's sorting algorithm is stable, so dictionaries with identical b values will retain their relative order).
from operator import itemgetter
tmp1 = sorted(mydictList, key=itemgetter('b'))
Next, use itertools.groupby to create subiterators that iterate over dictionaries with the same b value.
import itertools
tmp2 = itertools.groupby(tmp1, key=itemgetter('b))
Finally, create a new list that contains only the first element of each subiterator:
# Each x is a tuple (some-b-value, iterator-over-dicts-with-b-equal-some-b-value)
newdictList = [ next(x[1]) for x in tmp2 ]
Putting it all together:
from itertools import groupby
from operator import itemgetter
by_b = itemgetter('b')
newdictList = [ next(x[1]) for x in groupby(sorted(mydictList, key=by_b), key=by_b) ]
A very straight forward approach can go something like this:
mydictList= [{'a':1,'b':2,'c':3},{'a':2,'b':2,'c':4},{'a':2,'b':3,'c':4}]
b_set = set()
new_list = []
for d in mydictList:
if d['b'] not in b_set:
new_list.append(d)
b_set.add(d['b'])
Result:
>>> new_list
[{'a': 1, 'c': 3, 'b': 2}, {'a': 2, 'c': 4, 'b': 3}]

How to get the index with the key in a dictionary?

I have the key of a python dictionary and I want to get the corresponding index in the dictionary. Suppose I have the following dictionary,
d = { 'a': 10, 'b': 20, 'c': 30}
Is there a combination of python functions so that I can get the index value of 1, given the key value 'b'?
d.??('b')
I know it can be achieved with a loop or lambda (with a loop embedded). Just thought there should be a more straightforward way.
Use OrderedDicts: http://docs.python.org/2/library/collections.html#collections.OrderedDict
>>> x = OrderedDict((("a", "1"), ("c", '3'), ("b", "2")))
>>> x["d"] = 4
>>> x.keys().index("d")
3
>>> x.keys().index("c")
1
For those using Python 3
>>> list(x.keys()).index("c")
1
Dictionaries in python (<3.6) have no order. You could use a list of tuples as your data structure instead.
d = { 'a': 10, 'b': 20, 'c': 30}
newd = [('a',10), ('b',20), ('c',30)]
Then this code could be used to find the locations of keys with a specific value
locations = [i for i, t in enumerate(newd) if t[0]=='b']
>>> [1]
You can simply send the dictionary to list and then you can select the index of the item you are looking for.
DictTest = {
'4000':{},
'4001':{},
'4002':{},
'4003':{},
'5000':{},
}
print(list(DictTest).index('4000'))
No, there is no straightforward way because Python dictionaries do not have a set ordering.
From the documentation:
Keys and values are listed in an arbitrary order which is non-random, varies across Python implementations, and depends on the dictionary’s history of insertions and deletions.
In other words, the 'index' of b depends entirely on what was inserted into and deleted from the mapping before:
>>> map={}
>>> map['b']=1
>>> map
{'b': 1}
>>> map['a']=1
>>> map
{'a': 1, 'b': 1}
>>> map['c']=1
>>> map
{'a': 1, 'c': 1, 'b': 1}
As of Python 2.7, you could use the collections.OrderedDict() type instead, if insertion order is important to your application.
#Creating dictionary
animals = {"Cat" : "Pat", "Dog" : "Pat", "Tiger" : "Wild"}
#Convert dictionary to list (array)
keys = list(animals)
#Printing 1st dictionary key by index
print(keys[0])
#Done :)

Categories