A = 314
if A == A == A:
print('True #1')
if A == A == 271:
print('True #2')
lie = 0
if lie is lie is lie:
print('no matter how white, how small,')
print('how incorporating of a smidgeon')
print('of truth there be in it.')
Result:
True #1
no matter how white, how small,
how incorporating of a smidgeon
of truth there be in it.
I know it is not normal to use two "="s and "is"s in the if sentence. But I would like to know how the Python interpreter intereprets the if statement.
Is the expression lie is lie is lie interpreted simultaneously, or short-circuit way?
This question has many answers already, but consider the function split into bytecode:
def f():
lie = 0
if lie is lie is lie:
print('Lie')
dis.dis(f)
2 0 LOAD_CONST 1 (0)
2 STORE_FAST 0 (lie)
3 4 LOAD_FAST 0 (lie)
6 LOAD_FAST 0 (lie)
8 DUP_TOP
10 ROT_THREE
12 COMPARE_OP 8 (is)
14 JUMP_IF_FALSE_OR_POP 22
16 LOAD_FAST 0 (lie)
18 COMPARE_OP 8 (is)
20 JUMP_FORWARD 4 (to 26)
>> 22 ROT_TWO
24 POP_TOP
>> 26 POP_JUMP_IF_FALSE 36
4 28 LOAD_GLOBAL 0 (print)
30 LOAD_CONST 2 ('Lie')
32 CALL_FUNCTION 1
34 POP_TOP
>> 36 LOAD_CONST 0 (None)
38 RETURN_VALUE
This suggests that all lies are being checked to see if they match, in a linear fashion. If one fails, it should break/return.
To confirm, consider:
>lie is lie is lie is lie is lie
True
>lie is not lie is lie is lie is lie is lie
False
>lie is lie is lie is lie is lie is not lie
False
It will be interpreted as:
lie = 0
if lie is lie and lie is lie:
...
What you've happened across is called operator chaining.
From the documentation on Comparisons:
Comparisons can be chained arbitrarily, e.g.,
x < y <= zis equivalent tox < y and y <= z, except thatyis evaluated only once (but in both caseszis not evaluated at all whenx < yis found to be false).
Emphasis mine.
So, this would mean lie is lie is lie is interpreted as (lie is lie) and (lie is lie), and nothing more.
More generally, a op b op c op d ... is evaluated the same as a op b and b op c and c op d ... and so on. The expression is parsed according to python's grammar rules. In particular;
comparison ::= or_expr ( comp_operator or_expr )*
comp_operator ::= "<" | ">" | "==" | ">=" | "<=" | "!="
| "is" ["not"] | ["not"] "in"
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With