Show that None is a singleton, and compare it with False and with an empty container.
None is a built-in constant that stands for the absence of a value. The interpreter creates exactly one None object, and every reference to None points at it. You can check that with the identity operator.
print(None is None) # True
x = None
y = None
print(x is y) # True, one object and two names
print(None == False) # False, it is not the same value
print(bool(None)) # False, but it is falsy
print(None or 'fallback') # fallback
# Every empty container is falsy as well.
values = [0, '', [], {}, None]
for value in values:
print(repr(value), '->', bool(value))
Two distinctions matter here, and people regularly mix them up. Falsy means that the object is treated as false in a boolean context, and None qualifies for that. Equal means that the object compares equal to another object, and None equals only None. So None is falsy but it is not equal to False, and an empty list is falsy but it is not equal to None either.
That gap is the reason why the correct test for a missing value is is None rather than == None, and why the correct test for a usable value is if value is not None rather than if value. The second mistake quietly throws away an empty string, a zero, or an empty list, and all of those are values that a function might legitimately return.
There is one more practical note. A function that returns nothing returns None without saying so, so a missing return statement cannot be told apart from an explicit return None. That is deliberate in Python, because there is no separate missing-value marker to be confused with, but it does mean that callers should check for None instead of assuming that a return value exists.