2

Can somebody explain this for me?

>>> None is None is None
True
>>> (None is None) is None
False

Doesn't the 'is' operator take 2 operands, compare objects from the left, and return Boolean?

vbstb
  • 1,261
  • 1
  • 10
  • 14
  • Not exactly a duplicate, the other question implies that one knows the chained expression feature and asks if it is applicable to `is`. – Ferdinand Beyer Oct 14 '17 at 05:43
  • @FerdinandBeyer mm, I leave it up to you if you want to re-open it. Frequently, people will dupe-target the famous [Least Astonishment” and the Mutable Default Argument](https://stackoverflow.com/questions/1132941/least-astonishment-and-the-mutable-default-argument) when another questions is really asking about *unexplained* behavior they are seeing as a result of it. I bet there are other potential duplicates, though. – juanpa.arrivillaga Oct 14 '17 at 05:46
  • Thanks for letting me know. I admit this is a duplicate, but I really couldn't find those article or references, so I had to ask. – vbstb Oct 14 '17 at 05:54
  • @juanpa.arrivillaga fine with me – Ferdinand Beyer Oct 14 '17 at 06:17
  • 1
    @vbstb: no worries, without knowing the term "chained expression", finding references to this feature is pretty hard. – Ferdinand Beyer Oct 14 '17 at 06:18
  • @Ferdinand Beyer Thanks. – vbstb Oct 14 '17 at 06:29

2 Answers2

3

Because it is being interpreted as a chained comparison:

comparison    ::=  or_expr ( comp_operator or_expr )*
comp_operator ::=  "<" | ">" | "==" | ">=" | "<=" | "!="
                   | "is" ["not"] | ["not"] "in"

Comparisons can be chained arbitrarily, e.g., x < y <= z is equivalent to x < y and y <= z, except that y is evaluated only once (but in both cases z is not evaluated at all when x < y is found to be false).

Formally, if a, b, c, …, y, z are expressions and op1, op2, …, opN are comparison operators, then a op1 b op2 c ... y opN z is equivalent to a op1 b and b op2 c and ... y opN z, except that each expression is evaluated at most once.

Thus, since is is a comparison operator, your first expression is equivalent to:

None is None and None is None
Ry-
  • 218,210
  • 55
  • 464
  • 476
juanpa.arrivillaga
  • 88,713
  • 10
  • 131
  • 172
-1

Compare with 2 < 3 < 4.

Is the 2nd None the same as the 1st None? Yes. Is the 3rd same as the 2nd? Yes.

OTOH, (True) is None is clearly False. The parentheses broke the chaining.

Evaluating lo < n < hi is a common python idiom, and that doesn't make you worried about an intermediate result of True < 4. Evaluating x is y is z is less common, but for your singleton None the three objects are identical.

J_H
  • 17,926
  • 4
  • 24
  • 44
  • 1
    This does not explain anything. Why is this the case? Just because some other, unrelated, operator has a similar behavior? – Mad Physicist Oct 14 '17 at 05:38