18

Various Python guides say to use x is None instead of x == None. Why is that? Equality is used for comparing values, so it seems natural to ask if x has the value None, denoted with == and not is. Can someone explain why is is the preferred form and show an example where the two do not give the same answer?

Thanks.

  • `None` isn't exactly a value. "None is frequently used to represent the absence of a value, as when default arguments are not passed to a function." https://docs.python.org/2/library/constants.html#None – Mark E. Haase Dec 16 '14 at 21:04

3 Answers3

14

The reason people use is is because there is no advantage to using ==. It is possible to write objects that compare equal to None, but it is uncommon.

class A(object):
    def __eq__(self, other):
        return True

print A() == None

Output:

True

The is operator is also faster, but I don't consider this fact important.

John Clements
  • 16,895
  • 3
  • 37
  • 52
Dietrich Epp
  • 205,541
  • 37
  • 345
  • 415
  • 3
    I guess you could also add that there is only ever one `None` object, and it has no value. Since all `None`s are the same object, you should use the object identity operator `is`. The comparison operator `==` is inappropriate because `None` has no value. – Hamish Jun 23 '12 at 04:29
  • 3
    @Hamish In what sense does it "have no value"? It *is* a value, just like every other object. – Marcin Jun 23 '12 at 04:45
  • Why is the `is` operator faster? The reasoning for None being valueless makes no sense to me still... seems arbitrary. How is `None` different from `False` or other values? It's a value equal to `None`... by definition –  Jun 23 '12 at 05:02
  • 5
    @user248237 the `is` operator is potentially faster because it can't be overloaded - there is no equivalent to the chain of calls that `a == b` potentially makes (usually: `a.__eq__(b)`, `b.__eq__(a)` and finally `a is b` - first one to return something other than `NotImplemented` wins). `is` only tests one thing, that Python knows about directly, and always gives you an answer after one test. `None` being valueless is tenuous, but you could think of it like a null C pointer - a pointer's value is what it points to, and a null pointer points to nothing. – lvc Jun 23 '12 at 05:51
  • 3
    @user248237 but the important thing is that `is None` and `is not None` say exactly what you mean - as DietrichEpp points out, it is *possible* that `x == None` can be overloaded to return True for a non-`None` `x`, possibly via a bug. `is` implies equality (usually, see `float('nan')` for the sole counter-example), but equality doesn't always imply identity even when comparing against singletons (you need the singleton on the LHS, to have its `__eq__` do `return self is other`, and to not compare it against something that subclasses it). `is` says what you mean - much easier than rules. – lvc Jun 23 '12 at 06:01
  • @lvc Also, `is` can be implemented directly (in CPython, for example, by comparing pointer values) and doesn't need to make a Python function call at all. – Karl Knechtel Jun 23 '12 at 12:57
  • This answer doesn't directly answer the question (semantic difference between the two operators). – John Clements Feb 17 '17 at 00:04
  • @JohnClements: I think we might have had a different reading of the question--it sounded to me like the person who asked the question already understood what the semantic difference was. – Dietrich Epp Feb 17 '17 at 02:54
11

The is keyword tests identity. It is not a comparison operator like ==. Using is does more than test whether two arguments have the same value and/or the same internal structure: namely, it tests whether the two actually refer to the same object in memory. There are numerous implications to this, one of them being that is cannot be overloaded, and another being that behavior differs between mutable and immutable types. For example, consider the following:

>>> l1 = range(5)
>>> l2 = range(5)
>>> l1 == l2
True
>>> l1 is l2
False
>>> l3 = l1
>>> l1 is l3
True
>>> s1 = "abcde"
>>> s2 = "abcde"
>>> s1 == s2
True
>>> s1 is s2
True

Here, because lists are mutable, they cannot share a location in memory, and consequently is and == yield discrepant results. On the other hand, strings are immutable, and therefore their memory may be pooled in some cases. Basically, is can only reliably be used for simple, immutable types, or in instances when multiple names point to exactly the same object in memory (such as the use of l3 in the above example), and its use indicates a desire to test identity rather than value. I would expect is to be slightly faster than == because it doesn't perform method lookup, but I could be mistaken. Of course, for complex container objects like lists or dicts, is should be much faster than == (O(1) vs. O(n), presumably). That said, the speed issue is mostly a moot point, as the two should not be regarded as interchangeable.

Greg E.
  • 2,722
  • 1
  • 16
  • 22
  • 1
    `is` only tests memory location in CPython - in other implementations, it is perfectly free to test other things too (eg, PyPy treats ints specially, letting value determine identity). String interning isn't guaranteed either. You *are* right about `is` not doing method lookups, though - `==` can do two of them (one for each operand) before falling back to an identity check, and either of those can apply any kindof crazy equality rule it wants - including comparing equal to a singleton. – lvc Jun 23 '12 at 06:07
  • @lvc, thanks for clarifying. Feel free to edit my post if it needs correcting. I don't claim to be an expert in CPython's internals, or in those of any other implementation. – Greg E. Jun 23 '12 at 06:10
  • I wouldn't call scheme's `eq?` predicate very precise, since a lot of behavior is unspecified. Its behavior is less specified/precise than `eqv?`, which is in turn less specified/precise than `equal?`. – Dietrich Epp Jun 23 '12 at 09:10
  • @DietrichEpp, it's been a long while since I've done any coding in Scheme, but IIRC `equal?` does nothing more than apply `eqv?` to sequence/container types like vectors, cons cells, etc. In particular, `equal?` will return `#t` when comparing distinct objects, stored in different locations in memory, that are structurally identical. Clearly, that doesn't parallel the behavior of `is`. I seem to recall that `eq?` was the most primitive/low-level identity predicate, that much of its behavior in practice defaulted to that of `eqv?`, and that a lot of situations were implementation-dependent. – Greg E. Jun 23 '12 at 09:37
  • @DietrichEpp, q.v., http://www.gnu.org/software/mit-scheme/documentation/mit-scheme-ref/Equivalence-Predicates.html, which specifies that `eq?` only returns `#t` when `eqv?` would, and that `eq?` could be done as a simple pointer comparison (whether this is the practice in specific implementations, I have no idea). I was groping for some analogy to Python's `is` in my explanation and for reasons that escape comprehension, `eq?` is what come bubbling up from my subconscious. Of all the Scheme predicates, it seems closest, though whether any Scheme predicate is apposite is another matter. – Greg E. Jun 23 '12 at 09:50
  • I wasn't actually comparing `eq?` to `is`, but pointing out that they are both the least precise tools for comparison, because they have the most leeway to produce different results. For example, `(eq? 2 2) ==> #f` is fine, `#t` is also fine. In Python, you can often find `100 + 100 is 200` but `200 + 200 is not 400`. (The `equal?` predicate has to do a lot more than simply recurse since it has to terminate even for circular input.) – Dietrich Epp Jun 23 '12 at 09:56
  • @DietrichEpp, yes, but I *was* comparing `eq?` to `is` as an analogous identity operator from another language. Nowhere did I suggest that people use `eq?` in place of more appropriate predicates, nor did I claim that the parallel is exact, so I'm not quite sure where your objection lies. In any case, it's obviously not the right tool in a lot of situations, and clearly both `eq?` and `eqv?` exhibit ambiguous or implementation-defined behavior. – Greg E. Jun 23 '12 at 10:00
  • @DietrichEpp, and if your point is that people should use pure comparison operators rather than identity predicates when value/structural equality is the important criterion, I agree unreservedly. Does my original response to the OP's question give a different impression? – Greg E. Jun 23 '12 at 10:07
  • I was responding to the comment that `eq?` is the most "semantically precise", when it is actually the least precisely defined operator. I wasn't trying to say anything else. – Dietrich Epp Jun 23 '12 at 20:07
  • @DietrichEpp, you're right, that was a poor choice of words. I'm deleting that whole reference. Thanks. – Greg E. Jun 23 '12 at 22:06
3

PEP 8 says: "Comparisons to singletons like None should always be done with 'is' or 'is not', never the equality operators." Here is a quite good explanation why:

http://jaredgrubb.blogspot.com/2009/04/python-is-none-vs-none.html

Maksym Polshcha
  • 18,030
  • 8
  • 52
  • 77