今天,CTO在一次采访中问我,这看起来像一个简单的问题,
此语句返回什么? :
None is None is None
我认为Python执行了第一个操作None is None
并返回True
。在那之后,它将比较True is None
并返回False
。但是,令我惊讶的是,正确的答案是True
。我正在尝试找到该问题的答案,但是经过几天的搜索,我什么都没找到。有人可以解释为什么会这样吗?
答案 0 :(得分:40)
字节码表明这里正在执行两次比较,中间是重复的:
>>> import dis
>>> def a():
... return None is None is None
...
>>> dis.dis(a)
2 0 LOAD_CONST 0 (None)
3 LOAD_CONST 0 (None)
6 DUP_TOP
7 ROT_THREE
8 COMPARE_OP 8 (is)
11 JUMP_IF_FALSE_OR_POP 21
14 LOAD_CONST 0 (None)
17 COMPARE_OP 8 (is)
20 RETURN_VALUE
>> 21 ROT_TWO
22 POP_TOP
23 RETURN_VALUE
如docs for comparisons中所述,这是因为这些运算符链接在一起。
a op b op c
将转换为a op b and b op c
(请注意,b
在字节码中是重复的,如上所示)
答案 1 :(得分:31)
有些人评论说, Python比较可以被链接。
为便于说明,在链接时,Python实际上对表达式进行了 ANDs 。
T 其基本原理是,像a < b < c
这样的表达式具有数学上的常规解释。因此,您的特定表达式None is None is None
会涉及到 identity 运算符。
所以基本上,这将转换为:
(None is None) and (None is None)
显然是True
这是Python docs
中的另一个示例其他信息
特别是因为这是一个采访问题,所以需要特别注意的是,这并不是所有语言之间的普遍行为。
正如我链接的文档中所述,
与C不同,Python中的所有比较操作都具有相同的优先级, 低于任何算术,移位或按位运算的结果 操作。
因此,让我们考虑一下10 > x > 2
表达式(因为is
运算符在C语言中无效)。
C的翻译(由于operator precedence)
((10 > x) > 2)
Python的翻译
(10 > x) and (x > 2)
答案 2 :(得分:10)
is
是比较运算符,as seen in the docs:
comparison ::= or_expr ( comp_operator or_expr )* comp_operator ::= "<" | ">" | "==" | ">=" | "<=" | "!=" | "is" ["not"] | ["not"] "in"
因此,就像其他比较运算符一样,它可以任意链接。所以
a = b = c = None
a is b is c
等效于
(a is b) and (b is c)