Are True, False, None keywords or built-ins in Python 3?
Question: So, in Python 2 it was clear. But in Python 3 I'm a little bit confused.

    
    
    >>> import builtins
    >>> dir(builtins)
    ['ArithmeticError', 'AssertionError', 'AttributeError', 'BaseException', 'BlockingIOError', 'BrokenPipeError', 'BufferError', 'BytesWarning', 'ChildProcessError', 'ConnectionAbortedError', 'ConnectionError', 'ConnectionRefusedError', 'ConnectionResetError', 'DeprecationWarning', 'EOFError', 'Ellipsis', 'EnvironmentError', 'Exception', 'False', 'FileExistsError', 'FileNotFoundError', 'FloatingPointError', 'FutureWarning', 'GeneratorExit', 'IOError', 'ImportError', 'ImportWarning', 'IndentationError', 'IndexError', 'InterruptedError', 'IsADirectoryError', 'KeyError', 'KeyboardInterrupt', 'LookupError', 'MemoryError', 'NameError', 'None', 'NotADirectoryError', 'NotImplemented', 'NotImplementedError', 'OSError', 'OverflowError', 'PendingDeprecationWarning', 'PermissionError', 'ProcessLookupError', 'ReferenceError', 'ResourceWarning', 'RuntimeError', 'RuntimeWarning', 'StopIteration', 'SyntaxError', 'SyntaxWarning', 'SystemError', 'SystemExit', 'TabError', 'TimeoutError', 'True', 'TypeError', 'UnboundLocalError', 'UnicodeDecodeError', 'UnicodeEncodeError', 'UnicodeError', 'UnicodeTranslateError', 'UnicodeWarning', 'UserWarning', 'ValueError', 'Warning', 'ZeroDivisionError', '__build_class__', '__debug__', '__doc__', '__import__', '__loader__', '__name__', '__package__', '__spec__', 'abs', 'all', 'any', 'ascii', 'bin', 'bool', 'bytearray', 'bytes', 'callable', 'chr', 'classmethod', 'compile', 'complex', 'copyright', 'credits', 'delattr', 'dict', 'dir', 'divmod', 'enumerate', 'eval', 'exec', 'exit', 'filter', 'float', 'format', 'frozenset', 'getattr', 'globals', 'hasattr', 'hash', 'help', 'hex', 'id', 'input', 'int', 'isinstance', 'issubclass', 'iter', 'len', 'license', 'list', 'locals', 'map', 'max', 'memoryview', 'min', 'next', 'object', 'oct', 'open', 'ord', 'pow', 'print', 'property', 'quit', 'range', 'repr', 'reversed', 'round', 'set', 'setattr', 'slice', 'sorted', 'staticmethod', 'str', 'sum', 'super', 'tuple', 'type', 'vars', 'zip']
    >>> import keyword
    >>> dir(keyword.kwlist)
    ['False', 'None', 'True', 'and', 'as', 'assert', 'break', 'class', 'continue', 'def', 'del', 'elif', 'else', 'except', 'finally', 'for', 'from', 'global', 'if', 'import', 'in', 'is', 'lambda', 'nonlocal', 'not', 'or', 'pass', 'raise', 'return', 'try', 'while', 'with', 'yield']
    

_True_ , _False_ and _None_ are present in both the _builtins_ module and the
_keywords_ module. Then how should I treat them? As a builtin classes or as a
keywords?


Answer: They are reserved words _and_ built-in values. From the [Python 3 What's
New](https://docs.python.org/3/whatsnew/3.0.html#changed-syntax):

> `True`, `False`, and `None` are reserved words. (2.6 partially enforced the
> restrictions on `None` already.)

This means you cannot use them as names, assigning a different value to them.
This prevents accidentally masking the built-in singleton values:

    
    
    >>> True = False
      File "<stdin>", line 1
    SyntaxError: can't assign to keyword
    

Also see [Guido van Rossum's history lesson on `None`, `True` and
`False`](http://python-history.blogspot.co.uk/2013/11/story-of-none-true-
false.html):

> I still forgot to answer whether None/True/False are literals or keywords.
> My answer is that they are both. They are keywords because that's how the
> parser recognizes them. They are literals because that's their role in
> expressions and because they stand for constant values.

With `True`, `False` and `None` classified as keywords, the Python compiler
can actually optimize their use, since you cannot (directly) rebind these
names Python can look them up as constants instead of globals, which is
faster.

Until Python 3.4 there were still some corner cases where the compiler would
issue a global lookup for these objects, see [issue
16619](http://bugs.python.org/issue16619). From Python 3.4 onwards the Python
parser has been extended to produce a new AST node `NameConstant` to ensure
that they are treated as constants everywhere.

