>> d2 = {"john":466, "peter":45} >>> d...">

What do comparison operators do on dictionaries?

I came across this:

>>> d1 = {"john":40, "peter":45}
>>> d2 = {"john":466, "peter":45}
>>> d1 > d2
False

      

What does the comparison operator do when comparing two dict and how does it output False

?

+3


source to share


3 answers


Since these dicts are of equal length, we will find the smallest key for which the corresponding values ​​are not equal, i.e. 'john'

... Then the dictates are compared by the value of this key.

Demo:

>>> d1 = {"john":40, "peter":45}
>>> d2 = {"john":466, "peter":45}
>>> d1 < d2
True
>>> d2['john'] = 39
>>> d1 < d2
False

      

This basic idea has hardly changed since the Guido commit from over 20 years ago:



$ git show a0a69b8
commit a0a69b8b429f3d4c91f1c432247cfda017505976
Author: Guido van Rossum <guido@python.org>
Date:   Thu Dec 5 21:55:55 1996 +0000

    Experimental new implementation of dictionary comparison.  This
    defines that a shorter dictionary is always smaller than a longer one.
    For dictionaries of the same size, the smallest differing element
    determines the outcome (which yields the same results as before,
    without explicit sorting).

      

This is undocumented and the dict comparison code has been removed in Python 3, so I won't rely on this for anything important. The relevant CPython source is here .

Fun fact: Apparently, in earlier versions of Python, some of the comparison comparisons might crash at runtime and even cause Windows 98 to restart . Heh.

+6


source


Dictionaries such as sets do not maintain a well-defined order for their elements. In addition, the concept of a subset usually does not make sense for dictionaries, so the DICT class does not support operators such as <

, The dictionary supports the concept of equivalence, with d1 == d2 if two dictionaries contain the same set of keys, value pairs.

So what can you do

d1 == d2  #d1 is equivalent to d2
d1 != d2  #d1 is not equivalent to d2

      

However, you cannot do > < >= <=

It's in python 3.

>>> a
{1: '1', 2: '2'}
>>> b
{1: '1', 2: '2'}
>>> a==b
True
>>> a<b
Traceback (most recent call last):
  File "<pyshell#31>", line 1, in <module>
    a<b
TypeError: unorderable types: dict() < dict()
>>> a>b
Traceback (most recent call last):
  File "<pyshell#32>", line 1, in <module>
    a>b
TypeError: unorderable types: dict() > dict()
>>> 

      

However, in python 2 take a look at this,

>>> a = {2:2}
>>> b = {2:2}
>>> a==b
True
>>> a<b
False
>>> a>b
False

      

But when key

the same and value

different

>>> a={3:1}
>>> b={3:2}
>>> a<b
True
>>> a>b
False

      

Again, if value

the same,

>>> a={3:0}
>>> b={3:0}
>>> a==b
True
>>> a<b
False
>>> a>b
False

      

But pay attention to this when the value in the first is dict

greater

>>> a={3:200}
>>> b={3:10}
>>> a<b
False
>>> a>b
True

      

Until now we had the same key

other values

, now let's change that

Now Key with the same value

>>> a={2:10}
>>> b={3:10}
>>> a<b
True
>>> a>b
False
>>> 
>>> a={10:10}
>>> b={1:10}
>>> a<b
False
>>> a>b
True

      



What you can get from this is Python 2 is checked, and if it's the same, only then the value is checked. Now let's have different keys, different meanings,

>>> a={10:10}
>>> b={1:100}
>>> a<b
False
>>> a>b
True

      

Aha! In this case, you can infer that key

is the first thing that will be checked, and if they are the same, then the value will be checked. Now let's say there is more than one pair in our dictionary key:value

?

>>> a={10:10,1:10}
>>> b={10:10,2:10}
>>> a<b
True
>>> a>b
False
>>> a={10:10,200:10}
>>> b={10:10,1:10}
>>> a<b
False
>>> a>b
True

      

So it means. Each one is key

checked and then, if it key

is the same value, will be checked. Ah, but how does key verification work? For this take a look at the source code of dict_compare

NOTE: The cmp () method returns the sign of the difference between two numbers: -1 if x <y, 0 if x == y, or 1 if x> y

So what basically happens is that to compare dicts A and B the lengths are compared first (equal without issue). If they are not equal, return cmp (len (A), len (B)).

Then find the key akey

in A, which is the smallest key for which

akey not in B or A[akey] != B[akey]

→ (This only happens when akey is present in B).

(If there is no such key, then the dicts are equal.)

Also (necessary) find the smallest bkey in B for which

bkey not in A

 or -> A[bkey] != B[bkey]

(This only happens when bkey is present in B).

If akey! = Bkey, return cmp (akey, bkey). Else return cmp (A [akey], B [bkey])

>>> a={10:10,200:10}
>>> b={10:10,1:10}
>>> a<b
False
>>> a>b
True
>>> cmp(200,1)
1
>>> cmp(1,200)
-1

      

So, the smallest key in A

not in B

is equal 200

to 1

in A

.

Now internal python compares them according to the above algorithm, so it cmp(200,1)

will be calculated on run a>b

. Else cmp(1,200)

if done a<b

.

But this has been completely removed from python 3. It doesn't work in python 3.

+1


source


>>> d2>d1
True
>>> d3 = {"john":40, "peter":45}
>>> d1>=d3
True

      

As you can see above, comparing dictionaries made by key. They are equal;

>>> res = []
>>> for key1,val1 in d1.iteritems():
...     res.append(val1 >d2[key1] )
>>> res
[False, False]
>>> all(res)
False
>>> d1 > d2
False

      

-1


source







All Articles