Python Essentials for AI Engineer

Course Content

Python Essentials for AI Engineer

6 sections · 48 lessons

What is the difference between == and is?


What you need to know

Value vs identity

Python
a = [1, 2, 3]b = [1, 2, 3]c = aprint(a == b, a is b)     # True False -> equal contents, two objectsprint(a is c)             # True       -> c is another name for aprint(id(a) == id(c))     # True

== can be customised by a class (it calls __eq__), so "equal" means whatever the class says. is cannot be overridden; it is a pure identity check, and it is very fast.

Why is on numbers and strings is unreliable

CPython pre-creates the integers from -5 to 256 and reuses them, and it reuses ("interns") some strings. So is can return True by accident:

Python
x = 256; y = int("256")print(x is y)            # True  -> both are the cached 256x = 1000; y = int("1000")print(x is y)            # False -> two different int objectsprint(x == y)            # True

This behaviour is an implementation detail, not a language rule. Python 3.8+ even prints a SyntaxWarning when you write is with a literal, such as x is 1000.

Why is None and not == None

None is a singleton — there is exactly one None object — so identity is the correct test. == None can be fooled: a class can define __eq__ to return anything, and in NumPy or pandas, array == None compares element by element and returns an array, not a single True/False.

For booleans, PEP 8 (Python's style guide) says to write if flag: — not if flag == True: and not if flag is True:.

A real-life example

A retrieval function returns a relevance score, or None when the search failed. A score of 0.0 is a real result: "nothing relevant".

Python
def next_step(score):    if not score:                  # BUG: treats 0.0 like None        return "retry search"    return "use results"def next_step_fixed(score):    if score is None:              # only a missing score triggers a retry        return "retry search"    return "use results" if score > 0.5 else "fallback answer"print(next_step(0.0), "|", next_step_fixed(0.0))    # retry search | fallback answerprint(next_step_fixed(None))                        # retry search

The buggy version retries every search that honestly found nothing, doubling API costs on hard queries. is None says exactly what you mean.

Follow-up questions to expect

  • "What does is not do?" — The negated identity test. Write x is not None, which reads better than not x is None.
  • "Can a == b be True while a is b is False?" — Yes, whenever two separate objects hold equal values, like two lists with the same items.
  • "Can x == x be False?" — Yes: float("nan") == float("nan") is False, although x is x is always True.