Skip to content Skip to sidebar Skip to footer

Why Should You Avoid Using "is" And "is Not"?

I just started with Python and my online professor recommended using is and is not only when comparing a value to True, False, or None (or at least that is how I understood what he

Solution 1:

Python's is and == operators do two different things. You also can't compare is with JS's ===.

Simply, == tests if two identifiers are equal, while is tests whether two identifiers have the same memory address, therefore whether "they are each other"; the way they behave is just like it sounds:

#0 equals None, so returns True
0 == None

#But it isn't None, hence returns False
0 is None

#However, 0 is 0, so returns True
0 is 0

Solution 2:

Noneis a singleton, so you can compare object identity (is/is not) instead of equality (==/!=) - whenever you access None, you are getting the same object.

For almost all other cases, you should use equality (see e.g. Why does comparing strings in Python using either '==' or 'is' sometimes produce a different result?). In terms of "avoid[ing] forced type conversion" - Python is strongly typed and will never implicitly convert. Also, you can't really "cast" a type in Python - converting e.g. an int to str creates a new, separate object.

This is particularly important as None is often used to mark no return - if False or 0 or [] or anything else that evaluates False-y is a valid return, evaluating "truthiness" will give misleading results.

def yes_or_no(s):
    """Convert 'yes' or 'no' to boolean, or implicitly return None."""
    if s.lower() == "yes":
        return True
    elif s.lower() == "no":
        return False

result = some_func("foo")

if result: # wrong, covers None and False
    ...

if result is not None: # right, covers None only
    ...

Per the style guide:

Comparisons to singletons like None should always be done with is or is not, never the equality operators.

Also, beware of writing if x when you really mean if x is not None -- e.g. when testing whether a variable or argument that defaults to None was set to some other value. The other value might have a type (such as a container) that could be false in a boolean context!


Note that you generally don't compare True or False. Again, from the style guide:

Don't compare boolean values to True or False using ==.

Yes:   if greeting:
No:    if greeting == True:
Worse: if greeting is True:

See also: Use of True, False, and None as return values in python functions


Solution 3:

We shouldn't use is and is not for comparing values other than True, False and None, probably because of the following weird results:

>>> 20 is 19+1
True
>>> 19+1 is 20
True
>>> 1999+1 is 2000
False
>>> -0 is 0
True
>>> -0.0 is 0.0
False
>>> -0.0 is not 0.0
True
>>> 1999+1 is not 2000
True
>>> -0.0 == 0.0
True
>>> 1999+1 == 2000
True
>>> 1999+1 != 2000
False
>>> -0.0 != 0.0
False 

Post a Comment for "Why Should You Avoid Using "is" And "is Not"?"