在Python 2中,我们可以重新分配True
和False
(但不是None
),但全部三个(True
,False
和{{ 1}})被认为是内置变量。但是,在Py3k中,所有三个都按the docs更改为关键字。
从我自己的推测中,我只能猜测是为了防止像this这样的恶作剧来自旧的None
恶作剧。但是,在Python 2.7.5中,也许在之前,重新分配True, False = False, True
的{{1}}等语句引发了None = 3
。
从语义上讲,我不认为None
,SyntaxError: cannot assign to None
和True
是关键字,因为它们最后是语义文字,这就是Java所做的。我检查了PEP 0(索引),我找不到PEP解释它们被改变的原因。
是否有性能优势或其他原因使它们成为关键字而不是文字或特殊包装它们如python2中的False
?
答案 0 :(得分:44)
可能是因为Python 2.6不仅允许True = False
,还允许你说出有趣的话:
__builtin__.True = False
会在整个过程中将True
重置为False
。它可能导致真正有趣的事情发生:
>>> import __builtin__
>>> __builtin__.True = False
>>> True
False
>>> False
False
>>> __builtin__.False = True
>>> True
False
>>> False
False
编辑:正如Mike所指出的,Python wiki还在核心语言更改下声明了以下内容:
答案 1 :(得分:11)
主要有两个原因:
__builtin__.True = False
恶作剧。 (由devnull解释)答案 2 :(得分:3)
几个月前在python-dev上讨论过这个问题。 有大量链接到True的定义会很烦人,这与链接到例如nonlocal或with statements doc。
我得出的结论是,为什么“真与假”会使事情“更加精细”。
重新绑定为循环内调用的函数的副作用。
改变True非常容易,例如:
def True():
print True
让用户代码重新绑定内置名称None,True和False没有很好的用例,这使得它们几乎只有关键字。
让程序必须在每一步中的符号表中查找“True”才发现True具有值True远非直观。 (这就是为什么1比True快。)
x = compile('while 1:foop()','','exec')
dis.dis(x)的
0 SETUP_LOOP 19 (to 22)
3 JUMP_FORWARD 4 (to 10)
6 JUMP_IF_FALSE 11 (to 20)
9 POP_TOP
>> 10 LOAD_NAME 0 (foop)
13 CALL_FUNCTION 0
16 POP_TOP
17 JUMP_ABSOLUTE 10
>> 20 POP_TOP
21 POP_BLOCK
>> 22 LOAD_CONST 1 (None)
25 RETURN_VALUE
x = compile('while True:foop()','','exec')
dis.dis(x)的
0 SETUP_LOOP 19 (to 22)
>> 3 LOAD_NAME 0 (True)
6 JUMP_IF_FALSE 11 (to 20)
9 POP_TOP
10 LOAD_NAME 1 (foop)
13 CALL_FUNCTION 0
16 POP_TOP
17 JUMP_ABSOLUTE 3
>> 20 POP_TOP
21 POP_BLOCK
>> 22 LOAD_CONST 0 (None)
25 RETURN_VALUE
[alex@lancelot test]$ timeit.py -c -s'import itertools as it' 'c=it.count()'
'while True:' ' if c.next()>99: break'
10000 loops, best of 3: 91 usec per loop
[alex@lancelot test]$ timeit.py -c -s'import itertools as it' 'c=it.count()'
'while 1:' ' if c.next()>99: break'
10000 loops, best of 3: 76 usec per loop