Search code examples
python-3.8walrus-operator

Strange Behavior Python 3.8 Walrus Operator: chained inequalities


The following code:

a,b=1,2
print((x:=a)<2<(z:=b) or z>1>x)
print((x:=a)<1<(y:=b) or y>1>x)

gives the following output:

False
Traceback (most recent call last):
  File "C:/Users/phili/PycharmProjects/ML 1/CodingBat exercises.py", line 56, in <module>
    print((x:=a)<1<(y:=b) or y>1>x)
NameError: name 'y' is not defined

which seems absolutely inconsistent. Some variations like (x:=1)>=2>(y:=9) or y>=2>x also gives

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'y' is not defined

Does anyone know what's happening?


Solution

  • Apparently chained operators short-circuit. You can see this in this example code:

    >>> 1 < 1 < print("Nope")
    False  # Nothing else is printed
    

    This is likely because

    a < b < c
    

    Is essentially a short-hand of

    a < b and b < c
    

    And and short-circuits:

    >>> False and print("Nope")
    False
    

    This means that since the left-hand check is False, the right side is never evaluated, so y is never set.