From 00639fc954adfd94d74d39c451e3b5d54c53f2b4 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Fri, 18 Sep 2020 20:16:25 +0200 Subject: [PATCH 01/13] Reintroduced `types.EllipsisType` --- Lib/test/test_types.py | 4 ++++ Lib/types.py | 1 + 2 files changed, 5 insertions(+) diff --git a/Lib/test/test_types.py b/Lib/test/test_types.py index f499fb9c8c51a4..829c03b883c598 100644 --- a/Lib/test/test_types.py +++ b/Lib/test/test_types.py @@ -713,6 +713,10 @@ def test_or_type_repr(self): assert repr(int | None) == "int | None" assert repr(int | typing.GenericAlias(list, int)) == "int | list[int]" + def test_ellipsis_type(self): + self.assertIsInstance(Ellipsis, types.EllipsisType) + + class MappingProxyTests(unittest.TestCase): mappingproxy = types.MappingProxyType diff --git a/Lib/types.py b/Lib/types.py index 9642e7212caac6..12d7d42ceec39d 100644 --- a/Lib/types.py +++ b/Lib/types.py @@ -296,5 +296,6 @@ def wrapped(*args, **kwargs): GenericAlias = type(list[int]) Union = type(int | str) +EllipsisType = type(Ellipsis) __all__ = [n for n in globals() if n[:1] != '_'] From 0a97a885178adaf79d93041aed5bbab3c9e7d264 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Fri, 18 Sep 2020 20:17:20 +0200 Subject: [PATCH 02/13] Replaced `type(...)` and `type(ellipsis)` with `types.EllipsisType` --- Lib/ast.py | 5 +++-- Lib/copy.py | 6 +++--- Lib/lib2to3/fixes/fix_types.py | 1 - Lib/pickle.py | 4 ++-- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/Lib/ast.py b/Lib/ast.py index d860917f4d03ae..bb346f5c76ce57 100644 --- a/Lib/ast.py +++ b/Lib/ast.py @@ -24,6 +24,7 @@ :copyright: Copyright 2008 by Armin Ronacher. :license: Python License. """ +import types import sys from _ast import * from contextlib import contextmanager, nullcontext @@ -572,7 +573,7 @@ def __new__(cls, *args, **kwargs): Str: (str,), Bytes: (bytes,), NameConstant: (type(None), bool), - Ellipsis: (type(...),), + Ellipsis: (types.EllipsisType,), } _const_types_not = { Num: (bool,), @@ -586,7 +587,7 @@ def __new__(cls, *args, **kwargs): complex: 'Num', str: 'Str', bytes: 'Bytes', - type(...): 'Ellipsis', + types.EllipsisType: 'Ellipsis', } class slice(AST): diff --git a/Lib/copy.py b/Lib/copy.py index dd41c54dffe1d7..687215fe59fec5 100644 --- a/Lib/copy.py +++ b/Lib/copy.py @@ -108,8 +108,8 @@ def _copy_immutable(x): return x for t in (type(None), int, float, bool, complex, str, tuple, bytes, frozenset, type, range, slice, property, - types.BuiltinFunctionType, type(Ellipsis), type(NotImplemented), - types.FunctionType, weakref.ref): + types.BuiltinFunctionType, types.EllipsisType, + type(NotImplemented), types.FunctionType, weakref.ref): d[t] = _copy_immutable t = getattr(types, "CodeType", None) if t is not None: @@ -182,7 +182,7 @@ def deepcopy(x, memo=None, _nil=[]): def _deepcopy_atomic(x, memo): return x d[type(None)] = _deepcopy_atomic -d[type(Ellipsis)] = _deepcopy_atomic +d[types.EllipsisType] = _deepcopy_atomic d[type(NotImplemented)] = _deepcopy_atomic d[int] = _deepcopy_atomic d[float] = _deepcopy_atomic diff --git a/Lib/lib2to3/fixes/fix_types.py b/Lib/lib2to3/fixes/fix_types.py index 67bf51f2f5b85a..a5e5742812536f 100644 --- a/Lib/lib2to3/fixes/fix_types.py +++ b/Lib/lib2to3/fixes/fix_types.py @@ -30,7 +30,6 @@ 'ComplexType' : 'complex', 'DictType': 'dict', 'DictionaryType' : 'dict', - 'EllipsisType' : 'type(Ellipsis)', #'FileType' : 'io.IOBase', 'FloatType': 'float', 'IntType': 'int', diff --git a/Lib/pickle.py b/Lib/pickle.py index cbac5f168b45eb..77ce4872967023 100644 --- a/Lib/pickle.py +++ b/Lib/pickle.py @@ -23,7 +23,7 @@ """ -from types import FunctionType +from types import FunctionType, EllipsisType from copyreg import dispatch_table from copyreg import _extension_registry, _inverted_registry, _extension_cache from itertools import islice @@ -1121,7 +1121,7 @@ def save_type(self, obj): return self.save_reduce(type, (None,), obj=obj) elif obj is type(NotImplemented): return self.save_reduce(type, (NotImplemented,), obj=obj) - elif obj is type(...): + elif obj is EllipsisType: return self.save_reduce(type, (...,), obj=obj) return self.save_global(obj) From 8aecfd52580453da2410f2c69d299a5d99016365 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Fri, 18 Sep 2020 20:31:20 +0200 Subject: [PATCH 03/13] Added `EllipsisType` to the documentation --- Doc/library/constants.rst | 3 ++- Doc/library/types.rst | 7 +++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/Doc/library/constants.rst b/Doc/library/constants.rst index f17e1a37875168..9fd910d812b9a7 100644 --- a/Doc/library/constants.rst +++ b/Doc/library/constants.rst @@ -59,7 +59,8 @@ A small number of constants live in the built-in namespace. They are: .. index:: single: ...; ellipsis literal .. data:: Ellipsis - The same as the ellipsis literal "``...``". Special value used mostly in conjunction + The same as the ellipsis literal "``...``" and sole value of the type + :data:`types.EllipsisType`. Special value used mostly in conjunction with extended slicing syntax for user-defined container data types. diff --git a/Doc/library/types.rst b/Doc/library/types.rst index 79acdf4499afd2..64d76317f2bf9c 100644 --- a/Doc/library/types.rst +++ b/Doc/library/types.rst @@ -236,6 +236,13 @@ Standard names are defined for the following types: Defaults to ``None``. Previously the attribute was optional. +.. data:: EllipsisType + + The type of :data:`Ellipsis`. + + .. versionadded:: 3.10 + + .. class:: TracebackType(tb_next, tb_frame, tb_lasti, tb_lineno) The type of traceback objects such as found in ``sys.exc_info()[2]``. From 4066b4bbbfb952950b4e4659ba3f47f479695570 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Sun, 20 Sep 2020 15:15:47 +0200 Subject: [PATCH 04/13] Added Misc/NEWS.d and whatsnew entries --- Doc/whatsnew/3.10.rst | 6 ++++++ .../next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst | 1 + 2 files changed, 7 insertions(+) create mode 100644 Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst diff --git a/Doc/whatsnew/3.10.rst b/Doc/whatsnew/3.10.rst index ce888fec1d8c97..74fae2bd9a75ed 100644 --- a/Doc/whatsnew/3.10.rst +++ b/Doc/whatsnew/3.10.rst @@ -145,6 +145,12 @@ Add :data:`sys.orig_argv` attribute: the list of the original command line arguments passed to the Python executable. (Contributed by Victor Stinner in :issue:`23427`.) +types +----- + +Reintroduced the :data:`types.EllipsisType` class. +(Contributed by Bas van Beek in :issue:`41810`.) + unittest -------- diff --git a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst new file mode 100644 index 00000000000000..d04ff5a23a5355 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst @@ -0,0 +1 @@ +:data:`types.EllipsisType` has been reintroduced. From 307dcc1cc9f4f71dcd5d1f67012448e5e63a86c3 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Sun, 20 Sep 2020 15:20:34 +0200 Subject: [PATCH 05/13] Updated the acknowledgements --- Misc/ACKS | 1 + 1 file changed, 1 insertion(+) diff --git a/Misc/ACKS b/Misc/ACKS index d23797a2f55574..4023850e662dfd 100644 --- a/Misc/ACKS +++ b/Misc/ACKS @@ -134,6 +134,7 @@ Robin Becker Torsten Becker Bill Bedford MichaƂ Bednarski +Bas van Beek Ian Beer Stefan Behnel Reimer Behrends From 9fc1381b3e8ae8cb4fffb1e56df49ed899a64572 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 20:32:12 +0200 Subject: [PATCH 06/13] Reintroduced `types.NoneType` and `types.NotImplementedType` --- Lib/test/test_types.py | 6 ++++++ Lib/types.py | 2 ++ 2 files changed, 8 insertions(+) diff --git a/Lib/test/test_types.py b/Lib/test/test_types.py index 829c03b883c598..52a59d54f044d9 100644 --- a/Lib/test/test_types.py +++ b/Lib/test/test_types.py @@ -716,6 +716,12 @@ def test_or_type_repr(self): def test_ellipsis_type(self): self.assertIsInstance(Ellipsis, types.EllipsisType) + def test_notimplemented_type(self): + self.assertIsInstance(NotImplemented, types.NotImplementedType) + + def test_none_type(self): + self.assertIsInstance(None, types.NoneType) + class MappingProxyTests(unittest.TestCase): mappingproxy = types.MappingProxyType diff --git a/Lib/types.py b/Lib/types.py index 12d7d42ceec39d..532f4806fc0226 100644 --- a/Lib/types.py +++ b/Lib/types.py @@ -297,5 +297,7 @@ def wrapped(*args, **kwargs): Union = type(int | str) EllipsisType = type(Ellipsis) +NoneType = type(None) +NotImplementedType = type(NotImplemented) __all__ = [n for n in globals() if n[:1] != '_'] From 2791a239bacfe1f16e9672ca063cdb1f29e9a147 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 20:33:51 +0200 Subject: [PATCH 07/13] Replaced `type(NotImplemented)` and `type(None)` `type(NotImplemented)` and `type(None)` have, respectively, been replaced with `types.NotImplementedType` and `types.NoneType` --- Lib/ast.py | 4 ++-- Lib/copy.py | 8 ++++---- Lib/distutils/unixccompiler.py | 4 ++-- Lib/idlelib/run.py | 3 ++- Lib/imp.py | 2 +- Lib/inspect.py | 2 +- Lib/lib2to3/fixes/fix_types.py | 2 -- Lib/lib2to3/tests/test_fixers.py | 4 ---- Lib/pickle.py | 12 ++++++------ Lib/pickletools.py | 3 ++- Lib/pprint.py | 2 +- Lib/pydoc_data/topics.py | 2 +- Lib/random.py | 3 ++- Lib/runpy.py | 2 +- Lib/sqlite3/test/userfunctions.py | 9 +++++---- Lib/test/test_dataclasses.py | 5 +++-- Lib/test/test_descr.py | 22 +++++++++++----------- Lib/test/test_getargs2.py | 9 +++++---- Lib/test/test_nntplib.py | 3 ++- Lib/test/test_pwd.py | 3 ++- Lib/test/test_ssl.py | 3 ++- Lib/test/test_statistics.py | 3 ++- Lib/test/test_typing.py | 4 ++-- Lib/tkinter/__init__.py | 2 +- Lib/tkinter/ttk.py | 3 ++- Lib/typing.py | 16 ++++++++-------- Lib/unittest/test/testmock/testhelpers.py | 2 +- Lib/xmlrpc/client.py | 3 ++- 28 files changed, 73 insertions(+), 67 deletions(-) diff --git a/Lib/ast.py b/Lib/ast.py index bb346f5c76ce57..ce1f4533f68e67 100644 --- a/Lib/ast.py +++ b/Lib/ast.py @@ -572,7 +572,7 @@ def __new__(cls, *args, **kwargs): Num: (int, float, complex), Str: (str,), Bytes: (bytes,), - NameConstant: (type(None), bool), + NameConstant: (types.NoneType, bool), Ellipsis: (types.EllipsisType,), } _const_types_not = { @@ -581,7 +581,7 @@ def __new__(cls, *args, **kwargs): _const_node_type_names = { bool: 'NameConstant', # should be before int - type(None): 'NameConstant', + types.NoneType: 'NameConstant', int: 'Num', float: 'Num', complex: 'Num', diff --git a/Lib/copy.py b/Lib/copy.py index 687215fe59fec5..245c55d7f16312 100644 --- a/Lib/copy.py +++ b/Lib/copy.py @@ -106,10 +106,10 @@ def copy(x): def _copy_immutable(x): return x -for t in (type(None), int, float, bool, complex, str, tuple, +for t in (types.NoneType, int, float, bool, complex, str, tuple, bytes, frozenset, type, range, slice, property, types.BuiltinFunctionType, types.EllipsisType, - type(NotImplemented), types.FunctionType, weakref.ref): + types.NotImplementedType, types.FunctionType, weakref.ref): d[t] = _copy_immutable t = getattr(types, "CodeType", None) if t is not None: @@ -181,9 +181,9 @@ def deepcopy(x, memo=None, _nil=[]): def _deepcopy_atomic(x, memo): return x -d[type(None)] = _deepcopy_atomic +d[types.NoneType] = _deepcopy_atomic d[types.EllipsisType] = _deepcopy_atomic -d[type(NotImplemented)] = _deepcopy_atomic +d[types.NotImplementedType] = _deepcopy_atomic d[int] = _deepcopy_atomic d[float] = _deepcopy_atomic d[bool] = _deepcopy_atomic diff --git a/Lib/distutils/unixccompiler.py b/Lib/distutils/unixccompiler.py index 4d7a6de740ab3a..a97e9dfee40f17 100644 --- a/Lib/distutils/unixccompiler.py +++ b/Lib/distutils/unixccompiler.py @@ -13,7 +13,7 @@ * link shared library handled by 'cc -shared' """ -import os, sys, re +import os, sys, re, types from distutils import sysconfig from distutils.dep_util import newer @@ -157,7 +157,7 @@ def link(self, target_desc, objects, lib_opts = gen_lib_options(self, library_dirs, runtime_library_dirs, libraries) - if not isinstance(output_dir, (str, type(None))): + if not isinstance(output_dir, (str, types.NoneType)): raise TypeError("'output_dir' must be a string or None") if output_dir is not None: output_filename = os.path.join(output_dir, output_filename) diff --git a/Lib/idlelib/run.py b/Lib/idlelib/run.py index 1e84ecc6584ef1..963fdcf1afa47f 100644 --- a/Lib/idlelib/run.py +++ b/Lib/idlelib/run.py @@ -15,6 +15,7 @@ import _thread as thread import threading import warnings +import types from idlelib import autocomplete # AutoComplete, fetch_encodings from idlelib import calltip # Calltip @@ -558,7 +559,7 @@ def runcode(self, code): except SystemExit as e: if e.args: # SystemExit called with an argument. ob = e.args[0] - if not isinstance(ob, (type(None), int)): + if not isinstance(ob, (types.NoneType, int)): print('SystemExit: ' + str(ob), file=sys.stderr) # Return to the interactive prompt. except: diff --git a/Lib/imp.py b/Lib/imp.py index 31f8c766381adc..32d175e20b7637 100644 --- a/Lib/imp.py +++ b/Lib/imp.py @@ -264,7 +264,7 @@ def find_module(name, path=None): """ if not isinstance(name, str): raise TypeError("'name' must be a str, not {}".format(type(name))) - elif not isinstance(path, (type(None), list)): + elif not isinstance(path, (types.NoneType, list)): # Backwards-compatibility raise RuntimeError("'path' must be None or a list, " "not {}".format(type(path))) diff --git a/Lib/inspect.py b/Lib/inspect.py index 887a3424057b6e..15a2759f388226 100644 --- a/Lib/inspect.py +++ b/Lib/inspect.py @@ -2034,7 +2034,7 @@ def wrap_value(s): except NameError: raise RuntimeError() - if isinstance(value, (str, int, float, bytes, bool, type(None))): + if isinstance(value, (str, int, float, bytes, bool, types.NoneType)): return ast.Constant(value) raise RuntimeError() diff --git a/Lib/lib2to3/fixes/fix_types.py b/Lib/lib2to3/fixes/fix_types.py index a5e5742812536f..a17c99e497d432 100644 --- a/Lib/lib2to3/fixes/fix_types.py +++ b/Lib/lib2to3/fixes/fix_types.py @@ -36,8 +36,6 @@ 'ListType': 'list', 'LongType': 'int', 'ObjectType' : 'object', - 'NoneType': 'type(None)', - 'NotImplementedType' : 'type(NotImplemented)', 'SliceType' : 'slice', 'StringType': 'bytes', # XXX ? 'StringTypes' : '(str,)', # XXX ? diff --git a/Lib/lib2to3/tests/test_fixers.py b/Lib/lib2to3/tests/test_fixers.py index 121ebe68e5402b..33ff1cc51a61a5 100644 --- a/Lib/lib2to3/tests/test_fixers.py +++ b/Lib/lib2to3/tests/test_fixers.py @@ -3276,10 +3276,6 @@ def test_basic_types_convert(self): a = """int""" self.check(b, a) - b = """types.NoneType""" - a = """type(None)""" - self.check(b, a) - b = "types.StringTypes" a = "(str,)" self.check(b, a) diff --git a/Lib/pickle.py b/Lib/pickle.py index 77ce4872967023..13c988d1320f4e 100644 --- a/Lib/pickle.py +++ b/Lib/pickle.py @@ -23,7 +23,7 @@ """ -from types import FunctionType, EllipsisType +import types from copyreg import dispatch_table from copyreg import _extension_registry, _inverted_registry, _extension_cache from itertools import islice @@ -737,7 +737,7 @@ def save_reduce(self, func, args, state=None, listitems=None, def save_none(self, obj): self.write(NONE) - dispatch[type(None)] = save_none + dispatch[types.NoneType] = save_none def save_bool(self, obj): if self.proto >= 2: @@ -1117,15 +1117,15 @@ def save_global(self, obj, name=None): self.memoize(obj) def save_type(self, obj): - if obj is type(None): + if obj is types.NoneType: return self.save_reduce(type, (None,), obj=obj) - elif obj is type(NotImplemented): + elif obj is types.NotImplementedType: return self.save_reduce(type, (NotImplemented,), obj=obj) - elif obj is EllipsisType: + elif obj is types.EllipsisType: return self.save_reduce(type, (...,), obj=obj) return self.save_global(obj) - dispatch[FunctionType] = save_global + dispatch[types.FunctionType] = save_global dispatch[type] = save_type diff --git a/Lib/pickletools.py b/Lib/pickletools.py index 95706e746c9870..ca681b0f03f5ad 100644 --- a/Lib/pickletools.py +++ b/Lib/pickletools.py @@ -15,6 +15,7 @@ import pickle import re import sys +import types __all__ = ['dis', 'genops', 'optimize'] @@ -1017,7 +1018,7 @@ def __repr__(self): pynone = StackObject( name="None", - obtype=type(None), + obtype=types.NoneType, doc="The Python None object.") pytuple = StackObject( diff --git a/Lib/pprint.py b/Lib/pprint.py index 213998e3491ef7..35fabe450dacbc 100644 --- a/Lib/pprint.py +++ b/Lib/pprint.py @@ -591,7 +591,7 @@ def _safe_repr(object, context, maxlevels, level, sort_dicts): return rep, (rep and not rep.startswith('<')), False _builtin_scalars = frozenset({str, bytes, bytearray, int, float, complex, - bool, type(None)}) + bool, _types.NoneType}) def _recursion(object): return ("" diff --git a/Lib/pydoc_data/topics.py b/Lib/pydoc_data/topics.py index 8aca5c0cb88e38..f4790eb4e27275 100644 --- a/Lib/pydoc_data/topics.py +++ b/Lib/pydoc_data/topics.py @@ -1365,7 +1365,7 @@ 'explicitly return a\n' 'value. It supports no special operations. There is ' 'exactly one null\n' - 'object, named "None" (a built-in name). "type(None)()" ' + 'object, named "None" (a built-in name). "types.NoneType()" ' 'produces the\n' 'same singleton.\n' '\n' diff --git a/Lib/random.py b/Lib/random.py index 3ea369b81b3e50..e4a7597af64c00 100644 --- a/Lib/random.py +++ b/Lib/random.py @@ -55,6 +55,7 @@ from bisect import bisect as _bisect import os as _os import _random +import types try: # hashlib is pretty heavy to load, try lean internal module first @@ -154,7 +155,7 @@ def seed(self, a=None, version=2): a += _sha512(a).digest() a = int.from_bytes(a, 'big') - elif not isinstance(a, (type(None), int, float, str, bytes, bytearray)): + elif not isinstance(a, (types.NoneType, int, float, str, bytes, bytearray)): _warn('Seeding based on hashing is deprecated\n' 'since Python 3.9 and will be removed in a subsequent ' 'version. The only \n' diff --git a/Lib/runpy.py b/Lib/runpy.py index 7e1e1ac5dde2df..c27c5bc9959857 100644 --- a/Lib/runpy.py +++ b/Lib/runpy.py @@ -261,7 +261,7 @@ def run_path(path_name, init_globals=None, run_name=None): if type(importer).__module__ == 'imp': if type(importer).__name__ == 'NullImporter': is_NullImporter = True - if isinstance(importer, type(None)) or is_NullImporter: + if isinstance(importer, types.NoneType) or is_NullImporter: # Not a valid sys.path entry, so run the code directly # execfile() doesn't help as we want to allow compiled files code, fname = _get_code_from_file(run_name, path_name) diff --git a/Lib/sqlite3/test/userfunctions.py b/Lib/sqlite3/test/userfunctions.py index c11c82e1275778..27b429ce84225f 100644 --- a/Lib/sqlite3/test/userfunctions.py +++ b/Lib/sqlite3/test/userfunctions.py @@ -21,6 +21,7 @@ # misrepresented as being the original software. # 3. This notice may not be removed or altered from any source distribution. +import types import unittest import unittest.mock import sqlite3 as sqlite @@ -49,7 +50,7 @@ def func_isint(v): def func_isfloat(v): return type(v) is float def func_isnone(v): - return type(v) is type(None) + return type(v) is types.NoneType def func_isblob(v): return isinstance(v, (bytes, memoryview)) def func_islonglong(v): @@ -107,7 +108,7 @@ def __init__(self): self.val = None def step(self, whichType, val): - theType = {"str": str, "int": int, "float": float, "None": type(None), + theType = {"str": str, "int": int, "float": float, "None": types.NoneType, "blob": bytes} self.val = int(theType[whichType] is type(val)) @@ -119,7 +120,7 @@ def __init__(self): self.val = 0 def step(self, whichType, *vals): - theType = {"str": str, "int": int, "float": float, "None": type(None), + theType = {"str": str, "int": int, "float": float, "None": types.NoneType, "blob": bytes} for val in vals: self.val += int(theType[whichType] is type(val)) @@ -211,7 +212,7 @@ def CheckFuncReturnNull(self): cur = self.con.cursor() cur.execute("select returnnull()") val = cur.fetchone()[0] - self.assertEqual(type(val), type(None)) + self.assertEqual(type(val), types.NoneType) self.assertEqual(val, None) def CheckFuncReturnBlob(self): diff --git a/Lib/test/test_dataclasses.py b/Lib/test/test_dataclasses.py index b20103bdce51cb..8005f4f361c4b7 100644 --- a/Lib/test/test_dataclasses.py +++ b/Lib/test/test_dataclasses.py @@ -8,6 +8,7 @@ import inspect import builtins import unittest +import types from unittest.mock import Mock from typing import ClassVar, Any, List, Union, Tuple, Dict, Generic, TypeVar, Optional from typing import get_type_hints @@ -2026,7 +2027,7 @@ class C: def test_docstring_one_field_with_default_none(self): @dataclass class C: - x: Union[int, type(None)] = None + x: Union[int, types.NoneType] = None self.assertDocStrEqual(C.__doc__, "C(x:Optional[int]=None)") @@ -2955,7 +2956,7 @@ def test_text_annotations(self): self.assertEqual( get_type_hints(dataclass_textanno.Bar.__init__), {'foo': dataclass_textanno.Foo, - 'return': type(None)}) + 'return': types.NoneType}) class TestMakeDataclass(unittest.TestCase): diff --git a/Lib/test/test_descr.py b/Lib/test/test_descr.py index 307416c3300ae3..0d2e402f53ae77 100644 --- a/Lib/test/test_descr.py +++ b/Lib/test/test_descr.py @@ -3260,7 +3260,7 @@ class Int(int): __slots__ = [] cant(2, bool) o = object() cant(o, type(1)) - cant(o, type(None)) + cant(o, types.NoneType) del o class G(object): __slots__ = ["a", "b"] @@ -4000,35 +4000,35 @@ class D(C): def test_unsubclassable_types(self): with self.assertRaises(TypeError): - class X(type(None)): + class X(types.NoneType): pass with self.assertRaises(TypeError): - class X(object, type(None)): + class X(object, types.NoneType): pass with self.assertRaises(TypeError): - class X(type(None), object): + class X(types.NoneType, object): pass class O(object): pass with self.assertRaises(TypeError): - class X(O, type(None)): + class X(O, types.NoneType): pass with self.assertRaises(TypeError): - class X(type(None), O): + class X(types.NoneType, O): pass class X(object): pass with self.assertRaises(TypeError): - X.__bases__ = type(None), + X.__bases__ = types.NoneType, with self.assertRaises(TypeError): - X.__bases__ = object, type(None) + X.__bases__ = object, types.NoneType with self.assertRaises(TypeError): - X.__bases__ = type(None), object + X.__bases__ = types.NoneType, object with self.assertRaises(TypeError): - X.__bases__ = O, type(None) + X.__bases__ = O, types.NoneType with self.assertRaises(TypeError): - X.__bases__ = type(None), O + X.__bases__ = types.NoneType, O def test_mutable_bases_with_failing_mro(self): # Testing mutable bases with failing mro... diff --git a/Lib/test/test_getargs2.py b/Lib/test/test_getargs2.py index 09560197913059..1803adc0b8ab8e 100644 --- a/Lib/test/test_getargs2.py +++ b/Lib/test/test_getargs2.py @@ -2,6 +2,7 @@ import math import string import sys +import types from test import support from test.support import import_helper # Skip this test if the _testcapi module isn't available. @@ -567,11 +568,11 @@ def test_args(self): ret = get_args() self.assertIn(ret, ((), None)) - self.assertIn(type(ret), (tuple, type(None))) + self.assertIn(type(ret), (tuple, types.NoneType)) ret = get_args(*()) self.assertIn(ret, ((), None)) - self.assertIn(type(ret), (tuple, type(None))) + self.assertIn(type(ret), (tuple, types.NoneType)) def test_tuple(self): from _testcapi import getargs_tuple @@ -605,11 +606,11 @@ def test_kwargs(self): ret = get_kwargs() self.assertIn(ret, ({}, None)) - self.assertIn(type(ret), (dict, type(None))) + self.assertIn(type(ret), (dict, types.NoneType)) ret = get_kwargs(**{}) self.assertIn(ret, ({}, None)) - self.assertIn(type(ret), (dict, type(None))) + self.assertIn(type(ret), (dict, types.NoneType)) def test_positional_args(self): # using all positional args diff --git a/Lib/test/test_nntplib.py b/Lib/test/test_nntplib.py index b11c19c84d3fb1..4a21e96033f032 100644 --- a/Lib/test/test_nntplib.py +++ b/Lib/test/test_nntplib.py @@ -9,6 +9,7 @@ import os.path import re import threading +import types from test import support from test.support import socket_helper @@ -126,7 +127,7 @@ def _check_art_dict(self, art_dict): "references", ":bytes", ":lines"} ) for v in art_dict.values(): - self.assertIsInstance(v, (str, type(None))) + self.assertIsInstance(v, (str, types.NoneType)) def test_xover(self): resp, count, first, last, name = self.server.group(self.GROUP_NAME) diff --git a/Lib/test/test_pwd.py b/Lib/test/test_pwd.py index f8f12571ca90e0..67602147660c56 100644 --- a/Lib/test/test_pwd.py +++ b/Lib/test/test_pwd.py @@ -1,5 +1,6 @@ import sys import unittest +import types from test.support import import_helper pwd = import_helper.import_module('pwd') @@ -21,7 +22,7 @@ def test_values(self): self.assertEqual(e[3], e.pw_gid) self.assertIsInstance(e.pw_gid, int) self.assertEqual(e[4], e.pw_gecos) - self.assertIn(type(e.pw_gecos), (str, type(None))) + self.assertIn(type(e.pw_gecos), (str, types.NoneType)) self.assertEqual(e[5], e.pw_dir) self.assertIsInstance(e.pw_dir, str) self.assertEqual(e[6], e.pw_shell) diff --git a/Lib/test/test_ssl.py b/Lib/test/test_ssl.py index 26eec969a82e0d..60f52c1a9308ca 100644 --- a/Lib/test/test_ssl.py +++ b/Lib/test/test_ssl.py @@ -25,6 +25,7 @@ import platform import sysconfig import functools +import types try: import ctypes except ImportError: @@ -971,7 +972,7 @@ def test_asn1object(self): self.assertIsInstance(obj.nid, int) self.assertIsInstance(obj.shortname, str) self.assertIsInstance(obj.longname, str) - self.assertIsInstance(obj.oid, (str, type(None))) + self.assertIsInstance(obj.oid, (str, types.NoneType)) val = ssl._ASN1Object.fromname('TLS Web Server Authentication') self.assertEqual(val, expected) diff --git a/Lib/test/test_statistics.py b/Lib/test/test_statistics.py index 997110732a1765..a6695f1318ce3f 100644 --- a/Lib/test/test_statistics.py +++ b/Lib/test/test_statistics.py @@ -14,6 +14,7 @@ import random import sys import unittest +import types from test import support from test.support import import_helper @@ -937,7 +938,7 @@ def test_float(self): self.check_type_coercions(float) def test_non_numeric_types(self): - for bad_type in (str, list, type(None), tuple, dict): + for bad_type in (str, list, types.NoneType, tuple, dict): for good_type in (int, float, Fraction, Decimal): self.assertCoerceRaises(good_type, bad_type) diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index 42aa430c5e107e..3465cf9fb0e4ce 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -2845,7 +2845,7 @@ def test_get_type_hints_classes(self): self.assertEqual(gth(ann_module.S), {'x': str, 'y': str}) self.assertEqual(gth(ann_module.foo), {'x': int}) self.assertEqual(gth(NoneAndForward), - {'parent': NoneAndForward, 'meaning': type(None)}) + {'parent': NoneAndForward, 'meaning': types.NoneType}) self.assertEqual(gth(HasForeignBaseClass), {'some_xrepr': XRepr, 'other_a': mod_generics_cache.A, 'some_b': mod_generics_cache.B}) @@ -2885,7 +2885,7 @@ def testf(x, y): ... testf.__annotations__['x'] = 'int' self.assertEqual(gth(testf), {'x': int}) def testg(x: None): ... - self.assertEqual(gth(testg), {'x': type(None)}) + self.assertEqual(gth(testg), {'x': types.NoneType}) def test_get_type_hints_for_object_with_annotations(self): class A: ... diff --git a/Lib/tkinter/__init__.py b/Lib/tkinter/__init__.py index 1067ab6a8b8a1d..0a5988dd61cecc 100644 --- a/Lib/tkinter/__init__.py +++ b/Lib/tkinter/__init__.py @@ -102,7 +102,7 @@ def _cnfmerge(cnfs): """Internal function.""" if isinstance(cnfs, dict): return cnfs - elif isinstance(cnfs, (type(None), str)): + elif isinstance(cnfs, (types.NoneType, str)): return cnfs else: cnf = {} diff --git a/Lib/tkinter/ttk.py b/Lib/tkinter/ttk.py index c7c71cd5a559cf..3b32b1b95994d4 100644 --- a/Lib/tkinter/ttk.py +++ b/Lib/tkinter/ttk.py @@ -25,6 +25,7 @@ # functions "tclobjs_to_py", "setup_master"] +import types import tkinter from tkinter import _flatten, _join, _stringify, _splitdict @@ -1085,7 +1086,7 @@ def configure(self, cnf=None, **kw): Setting a value for any of the "from", "from_" or "to" options generates a <> event.""" retval = Widget.configure(self, cnf, **kw) - if not isinstance(cnf, (type(None), str)): + if not isinstance(cnf, (types.NoneType, str)): kw.update(cnf) if any(['from' in kw, 'from_' in kw, 'to' in kw]): self.event_generate('<>') diff --git a/Lib/typing.py b/Lib/typing.py index 8c61bd8e084a85..356cab9cc3b0b8 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -121,7 +121,7 @@ def _type_check(arg, msg, is_argument=True): """Check that the argument is a type, and return it (internal helper). - As a special case, accept None and return type(None) instead. Also wrap strings + As a special case, accept None and return types.NoneType instead. Also wrap strings into ForwardRef instances. Consider several corner cases, for example plain special forms like Union are not valid, while Union[int, str] is OK, etc. The msg argument is a human-readable error message, e.g:: @@ -135,7 +135,7 @@ def _type_check(arg, msg, is_argument=True): invalid_generic_forms = invalid_generic_forms + (ClassVar, Final) if arg is None: - return type(None) + return types.NoneType if isinstance(arg, str): return ForwardRef(arg) if (isinstance(arg, _GenericAlias) and @@ -392,7 +392,7 @@ def Union(self, parameters): To define a union, use e.g. Union[int, str]. Details: - The arguments must be types and there must be at least one. - None as an argument is a special case and is replaced by - type(None). + types.NoneType. - Unions of unions are flattened, e.g.:: Union[Union[int, str], float] == Union[int, str, float] @@ -430,7 +430,7 @@ def Optional(self, parameters): Optional[X] is equivalent to Union[X, None]. """ arg = _type_check(parameters, f"{self} requires a single type.") - return Union[arg, type(None)] + return Union[arg, types.NoneType] @_SpecialForm def Literal(self, parameters): @@ -889,9 +889,9 @@ def __hash__(self): def __repr__(self): args = self.__args__ if len(args) == 2: - if args[0] is type(None): + if args[0] is types.NoneType: return f'typing.Optional[{_type_repr(args[1])}]' - elif args[1] is type(None): + elif args[1] is types.NoneType: return f'typing.Optional[{_type_repr(args[0])}]' return super().__repr__() @@ -1374,7 +1374,7 @@ def get_type_hints(obj, globalns=None, localns=None, include_extras=False): ann = base.__dict__.get('__annotations__', {}) for name, value in ann.items(): if value is None: - value = type(None) + value = types.NoneType if isinstance(value, str): value = ForwardRef(value, is_argument=False) value = _eval_type(value, base_globals, localns) @@ -1406,7 +1406,7 @@ def get_type_hints(obj, globalns=None, localns=None, include_extras=False): hints = dict(hints) for name, value in hints.items(): if value is None: - value = type(None) + value = types.NoneType if isinstance(value, str): value = ForwardRef(value) value = _eval_type(value, globalns, localns) diff --git a/Lib/unittest/test/testmock/testhelpers.py b/Lib/unittest/test/testmock/testhelpers.py index 9e7ec5d62d5da2..10e7c35f0ae6ea 100644 --- a/Lib/unittest/test/testmock/testhelpers.py +++ b/Lib/unittest/test/testmock/testhelpers.py @@ -863,7 +863,7 @@ class Foo(object): mock = create_autospec(Foo) none = mock.bar - self.assertNotIsInstance(none, type(None)) + self.assertNotIsInstance(none, types.NoneType) none.foo() none.foo.assert_called_once_with() diff --git a/Lib/xmlrpc/client.py b/Lib/xmlrpc/client.py index d15d60d2937a82..575d67a0b3ff0f 100644 --- a/Lib/xmlrpc/client.py +++ b/Lib/xmlrpc/client.py @@ -138,6 +138,7 @@ from xml.parsers import expat import errno from io import BytesIO +import types try: import gzip except ImportError: @@ -533,7 +534,7 @@ def dump_nil (self, value, write): if not self.allow_none: raise TypeError("cannot marshal None unless allow_none is enabled") write("") - dispatch[type(None)] = dump_nil + dispatch[types.NoneType] = dump_nil def dump_bool(self, value, write): write("") From da1ab85ce2a913322f2ad30c3171ac7aecc70e37 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 20:34:38 +0200 Subject: [PATCH 08/13] Added `types.NoneType` & `types.NotImplementedType` to whatsnew and the docs --- Doc/library/constants.rst | 5 +++-- Doc/library/types.rst | 14 ++++++++++++++ Doc/whatsnew/3.10.rst | 3 ++- .../2020-09-20-15-14-05.bpo-41810.7l8lyV.rst | 3 ++- 4 files changed, 21 insertions(+), 4 deletions(-) diff --git a/Doc/library/constants.rst b/Doc/library/constants.rst index 9fd910d812b9a7..11bd0d2b4c89eb 100644 --- a/Doc/library/constants.rst +++ b/Doc/library/constants.rst @@ -19,14 +19,15 @@ A small number of constants live in the built-in namespace. They are: .. data:: None - The sole value of the type ``NoneType``. ``None`` is frequently used to + The sole value of the type :data:`types.NoneType`. ``None`` is frequently used to represent the absence of a value, as when default arguments are not passed to a function. Assignments to ``None`` are illegal and raise a :exc:`SyntaxError`. .. data:: NotImplemented - Special value which should be returned by the binary special methods + Sole value of the type :data:`types.NotImplementedType` and a + special value which should be returned by the binary special methods (e.g. :meth:`__eq__`, :meth:`__lt__`, :meth:`__add__`, :meth:`__rsub__`, etc.) to indicate that the operation is not implemented with respect to the other type; may be returned by the in-place binary special methods diff --git a/Doc/library/types.rst b/Doc/library/types.rst index 64d76317f2bf9c..25fa750f2ccacf 100644 --- a/Doc/library/types.rst +++ b/Doc/library/types.rst @@ -103,6 +103,13 @@ If you instantiate any of these types, note that signatures may vary between Pyt Standard names are defined for the following types: +.. data:: NoneType + + The type of :data:`None`. + + .. versionadded:: 3.10 + + .. data:: FunctionType LambdaType @@ -186,6 +193,13 @@ Standard names are defined for the following types: .. versionadded:: 3.7 +.. data:: NotImplementedType + + The type of :data:`NotImplemented`. + + .. versionadded:: 3.10 + + .. data:: MethodDescriptorType The type of methods of some built-in data types such as :meth:`str.join`. diff --git a/Doc/whatsnew/3.10.rst b/Doc/whatsnew/3.10.rst index 74fae2bd9a75ed..a55fee2b238fd5 100644 --- a/Doc/whatsnew/3.10.rst +++ b/Doc/whatsnew/3.10.rst @@ -148,7 +148,8 @@ arguments passed to the Python executable. types ----- -Reintroduced the :data:`types.EllipsisType` class. +Reintroduced the :data:`types.EllipsisType`, :data:`types.NoneType` +and :data:`types.NotImplementedType` classes. (Contributed by Bas van Beek in :issue:`41810`.) unittest diff --git a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst index d04ff5a23a5355..a04f0f5a49a17b 100644 --- a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst +++ b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst @@ -1 +1,2 @@ -:data:`types.EllipsisType` has been reintroduced. +:data:`types.EllipsisType`, :data:`types.EllipsisType` and +:data:`types.NoneType` have been reintroduced. From f682623aa3001a4ac19e727c3103cdb0dce8672e Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 22:28:58 +0200 Subject: [PATCH 09/13] Replaced a duplicate `EllipsisType` with `NotImplementedType` Addresses https://github.com/python/cpython/pull/22336#discussion_r492317442 --- .../NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst | 1 + 1 file changed, 1 insertion(+) diff --git a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst index a04f0f5a49a17b..38b35905f275b6 100644 --- a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst +++ b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst @@ -1,2 +1,3 @@ :data:`types.EllipsisType`, :data:`types.EllipsisType` and :data:`types.NoneType` have been reintroduced. +:data:`types.EllipsisType`, :data:`types.NotImplementedType` and From 370149882d2cea95f2fed7c732bcbb6ae343a3fe Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 22:30:19 +0200 Subject: [PATCH 10/13] Provide motivation for the type reintroduction Addresses https://github.com/python/cpython/pull/22336#discussion_r492317123 --- Doc/whatsnew/3.10.rst | 3 ++- .../next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst | 4 ++-- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/Doc/whatsnew/3.10.rst b/Doc/whatsnew/3.10.rst index a55fee2b238fd5..a5e28b3258fe7f 100644 --- a/Doc/whatsnew/3.10.rst +++ b/Doc/whatsnew/3.10.rst @@ -149,7 +149,8 @@ types ----- Reintroduced the :data:`types.EllipsisType`, :data:`types.NoneType` -and :data:`types.NotImplementedType` classes. +and :data:`types.NotImplementedType` classes, aforementioned types +now being useable as annotations. (Contributed by Bas van Beek in :issue:`41810`.) unittest diff --git a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst index 38b35905f275b6..c01e76285e5de7 100644 --- a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst +++ b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst @@ -1,3 +1,3 @@ -:data:`types.EllipsisType`, :data:`types.EllipsisType` and -:data:`types.NoneType` have been reintroduced. :data:`types.EllipsisType`, :data:`types.NotImplementedType` and +:data:`types.NoneType` have been reintroduced, aforementioned types +now being useable as annotations. From 33caa6fb32ec98766a9402670176ddde16d47738 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 22:48:43 +0200 Subject: [PATCH 11/13] Explicitly mention static type checkers --- Doc/whatsnew/3.10.rst | 4 ++-- .../next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Doc/whatsnew/3.10.rst b/Doc/whatsnew/3.10.rst index a5e28b3258fe7f..f88281a934ca19 100644 --- a/Doc/whatsnew/3.10.rst +++ b/Doc/whatsnew/3.10.rst @@ -149,8 +149,8 @@ types ----- Reintroduced the :data:`types.EllipsisType`, :data:`types.NoneType` -and :data:`types.NotImplementedType` classes, aforementioned types -now being useable as annotations. +and :data:`types.NotImplementedType` classes, providing a new set +of types readily interpretable by type checkers. (Contributed by Bas van Beek in :issue:`41810`.) unittest diff --git a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst index c01e76285e5de7..515aea9e36ce95 100644 --- a/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst +++ b/Misc/NEWS.d/next/Library/2020-09-20-15-14-05.bpo-41810.7l8lyV.rst @@ -1,3 +1,3 @@ :data:`types.EllipsisType`, :data:`types.NotImplementedType` and -:data:`types.NoneType` have been reintroduced, aforementioned types -now being useable as annotations. +:data:`types.NoneType` have been reintroduced, providing a new set +of types readily interpretable by static type checkers. From 84ebe183e0c4ed9059e88fbede11092759f3eb66 Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Mon, 21 Sep 2020 23:40:24 +0200 Subject: [PATCH 12/13] Revert the `type(...)` to `types....` replacements Reverts https://github.com/python/cpython/pull/22336/commits/2791a239bacfe1f16e9672ca063cdb1f29e9a147 and https://github.com/python/cpython/pull/22336/commits/0a97a885178adaf79d93041aed5bbab3c9e7d264. Save this for a follow up. --- Lib/ast.py | 9 ++++----- Lib/copy.py | 12 ++++++------ Lib/distutils/unixccompiler.py | 4 ++-- Lib/idlelib/run.py | 3 +-- Lib/imp.py | 2 +- Lib/inspect.py | 2 +- Lib/lib2to3/fixes/fix_types.py | 3 +++ Lib/lib2to3/tests/test_fixers.py | 4 ++++ Lib/pickle.py | 12 ++++++------ Lib/pickletools.py | 3 +-- Lib/pprint.py | 2 +- Lib/pydoc_data/topics.py | 2 +- Lib/random.py | 3 +-- Lib/runpy.py | 2 +- Lib/sqlite3/test/userfunctions.py | 9 ++++----- Lib/test/test_dataclasses.py | 5 ++--- Lib/test/test_descr.py | 22 +++++++++++----------- Lib/test/test_getargs2.py | 9 ++++----- Lib/test/test_nntplib.py | 3 +-- Lib/test/test_pwd.py | 3 +-- Lib/test/test_ssl.py | 3 +-- Lib/test/test_statistics.py | 3 +-- Lib/test/test_typing.py | 4 ++-- Lib/tkinter/__init__.py | 2 +- Lib/tkinter/ttk.py | 3 +-- Lib/typing.py | 16 ++++++++-------- Lib/unittest/test/testmock/testhelpers.py | 2 +- Lib/xmlrpc/client.py | 3 +-- 28 files changed, 72 insertions(+), 78 deletions(-) diff --git a/Lib/ast.py b/Lib/ast.py index ce1f4533f68e67..d860917f4d03ae 100644 --- a/Lib/ast.py +++ b/Lib/ast.py @@ -24,7 +24,6 @@ :copyright: Copyright 2008 by Armin Ronacher. :license: Python License. """ -import types import sys from _ast import * from contextlib import contextmanager, nullcontext @@ -572,8 +571,8 @@ def __new__(cls, *args, **kwargs): Num: (int, float, complex), Str: (str,), Bytes: (bytes,), - NameConstant: (types.NoneType, bool), - Ellipsis: (types.EllipsisType,), + NameConstant: (type(None), bool), + Ellipsis: (type(...),), } _const_types_not = { Num: (bool,), @@ -581,13 +580,13 @@ def __new__(cls, *args, **kwargs): _const_node_type_names = { bool: 'NameConstant', # should be before int - types.NoneType: 'NameConstant', + type(None): 'NameConstant', int: 'Num', float: 'Num', complex: 'Num', str: 'Str', bytes: 'Bytes', - types.EllipsisType: 'Ellipsis', + type(...): 'Ellipsis', } class slice(AST): diff --git a/Lib/copy.py b/Lib/copy.py index 245c55d7f16312..dd41c54dffe1d7 100644 --- a/Lib/copy.py +++ b/Lib/copy.py @@ -106,10 +106,10 @@ def copy(x): def _copy_immutable(x): return x -for t in (types.NoneType, int, float, bool, complex, str, tuple, +for t in (type(None), int, float, bool, complex, str, tuple, bytes, frozenset, type, range, slice, property, - types.BuiltinFunctionType, types.EllipsisType, - types.NotImplementedType, types.FunctionType, weakref.ref): + types.BuiltinFunctionType, type(Ellipsis), type(NotImplemented), + types.FunctionType, weakref.ref): d[t] = _copy_immutable t = getattr(types, "CodeType", None) if t is not None: @@ -181,9 +181,9 @@ def deepcopy(x, memo=None, _nil=[]): def _deepcopy_atomic(x, memo): return x -d[types.NoneType] = _deepcopy_atomic -d[types.EllipsisType] = _deepcopy_atomic -d[types.NotImplementedType] = _deepcopy_atomic +d[type(None)] = _deepcopy_atomic +d[type(Ellipsis)] = _deepcopy_atomic +d[type(NotImplemented)] = _deepcopy_atomic d[int] = _deepcopy_atomic d[float] = _deepcopy_atomic d[bool] = _deepcopy_atomic diff --git a/Lib/distutils/unixccompiler.py b/Lib/distutils/unixccompiler.py index a97e9dfee40f17..4d7a6de740ab3a 100644 --- a/Lib/distutils/unixccompiler.py +++ b/Lib/distutils/unixccompiler.py @@ -13,7 +13,7 @@ * link shared library handled by 'cc -shared' """ -import os, sys, re, types +import os, sys, re from distutils import sysconfig from distutils.dep_util import newer @@ -157,7 +157,7 @@ def link(self, target_desc, objects, lib_opts = gen_lib_options(self, library_dirs, runtime_library_dirs, libraries) - if not isinstance(output_dir, (str, types.NoneType)): + if not isinstance(output_dir, (str, type(None))): raise TypeError("'output_dir' must be a string or None") if output_dir is not None: output_filename = os.path.join(output_dir, output_filename) diff --git a/Lib/idlelib/run.py b/Lib/idlelib/run.py index 963fdcf1afa47f..1e84ecc6584ef1 100644 --- a/Lib/idlelib/run.py +++ b/Lib/idlelib/run.py @@ -15,7 +15,6 @@ import _thread as thread import threading import warnings -import types from idlelib import autocomplete # AutoComplete, fetch_encodings from idlelib import calltip # Calltip @@ -559,7 +558,7 @@ def runcode(self, code): except SystemExit as e: if e.args: # SystemExit called with an argument. ob = e.args[0] - if not isinstance(ob, (types.NoneType, int)): + if not isinstance(ob, (type(None), int)): print('SystemExit: ' + str(ob), file=sys.stderr) # Return to the interactive prompt. except: diff --git a/Lib/imp.py b/Lib/imp.py index 32d175e20b7637..31f8c766381adc 100644 --- a/Lib/imp.py +++ b/Lib/imp.py @@ -264,7 +264,7 @@ def find_module(name, path=None): """ if not isinstance(name, str): raise TypeError("'name' must be a str, not {}".format(type(name))) - elif not isinstance(path, (types.NoneType, list)): + elif not isinstance(path, (type(None), list)): # Backwards-compatibility raise RuntimeError("'path' must be None or a list, " "not {}".format(type(path))) diff --git a/Lib/inspect.py b/Lib/inspect.py index 15a2759f388226..887a3424057b6e 100644 --- a/Lib/inspect.py +++ b/Lib/inspect.py @@ -2034,7 +2034,7 @@ def wrap_value(s): except NameError: raise RuntimeError() - if isinstance(value, (str, int, float, bytes, bool, types.NoneType)): + if isinstance(value, (str, int, float, bytes, bool, type(None))): return ast.Constant(value) raise RuntimeError() diff --git a/Lib/lib2to3/fixes/fix_types.py b/Lib/lib2to3/fixes/fix_types.py index a17c99e497d432..67bf51f2f5b85a 100644 --- a/Lib/lib2to3/fixes/fix_types.py +++ b/Lib/lib2to3/fixes/fix_types.py @@ -30,12 +30,15 @@ 'ComplexType' : 'complex', 'DictType': 'dict', 'DictionaryType' : 'dict', + 'EllipsisType' : 'type(Ellipsis)', #'FileType' : 'io.IOBase', 'FloatType': 'float', 'IntType': 'int', 'ListType': 'list', 'LongType': 'int', 'ObjectType' : 'object', + 'NoneType': 'type(None)', + 'NotImplementedType' : 'type(NotImplemented)', 'SliceType' : 'slice', 'StringType': 'bytes', # XXX ? 'StringTypes' : '(str,)', # XXX ? diff --git a/Lib/lib2to3/tests/test_fixers.py b/Lib/lib2to3/tests/test_fixers.py index 33ff1cc51a61a5..121ebe68e5402b 100644 --- a/Lib/lib2to3/tests/test_fixers.py +++ b/Lib/lib2to3/tests/test_fixers.py @@ -3276,6 +3276,10 @@ def test_basic_types_convert(self): a = """int""" self.check(b, a) + b = """types.NoneType""" + a = """type(None)""" + self.check(b, a) + b = "types.StringTypes" a = "(str,)" self.check(b, a) diff --git a/Lib/pickle.py b/Lib/pickle.py index 13c988d1320f4e..cbac5f168b45eb 100644 --- a/Lib/pickle.py +++ b/Lib/pickle.py @@ -23,7 +23,7 @@ """ -import types +from types import FunctionType from copyreg import dispatch_table from copyreg import _extension_registry, _inverted_registry, _extension_cache from itertools import islice @@ -737,7 +737,7 @@ def save_reduce(self, func, args, state=None, listitems=None, def save_none(self, obj): self.write(NONE) - dispatch[types.NoneType] = save_none + dispatch[type(None)] = save_none def save_bool(self, obj): if self.proto >= 2: @@ -1117,15 +1117,15 @@ def save_global(self, obj, name=None): self.memoize(obj) def save_type(self, obj): - if obj is types.NoneType: + if obj is type(None): return self.save_reduce(type, (None,), obj=obj) - elif obj is types.NotImplementedType: + elif obj is type(NotImplemented): return self.save_reduce(type, (NotImplemented,), obj=obj) - elif obj is types.EllipsisType: + elif obj is type(...): return self.save_reduce(type, (...,), obj=obj) return self.save_global(obj) - dispatch[types.FunctionType] = save_global + dispatch[FunctionType] = save_global dispatch[type] = save_type diff --git a/Lib/pickletools.py b/Lib/pickletools.py index ca681b0f03f5ad..95706e746c9870 100644 --- a/Lib/pickletools.py +++ b/Lib/pickletools.py @@ -15,7 +15,6 @@ import pickle import re import sys -import types __all__ = ['dis', 'genops', 'optimize'] @@ -1018,7 +1017,7 @@ def __repr__(self): pynone = StackObject( name="None", - obtype=types.NoneType, + obtype=type(None), doc="The Python None object.") pytuple = StackObject( diff --git a/Lib/pprint.py b/Lib/pprint.py index 35fabe450dacbc..213998e3491ef7 100644 --- a/Lib/pprint.py +++ b/Lib/pprint.py @@ -591,7 +591,7 @@ def _safe_repr(object, context, maxlevels, level, sort_dicts): return rep, (rep and not rep.startswith('<')), False _builtin_scalars = frozenset({str, bytes, bytearray, int, float, complex, - bool, _types.NoneType}) + bool, type(None)}) def _recursion(object): return ("" diff --git a/Lib/pydoc_data/topics.py b/Lib/pydoc_data/topics.py index f4790eb4e27275..8aca5c0cb88e38 100644 --- a/Lib/pydoc_data/topics.py +++ b/Lib/pydoc_data/topics.py @@ -1365,7 +1365,7 @@ 'explicitly return a\n' 'value. It supports no special operations. There is ' 'exactly one null\n' - 'object, named "None" (a built-in name). "types.NoneType()" ' + 'object, named "None" (a built-in name). "type(None)()" ' 'produces the\n' 'same singleton.\n' '\n' diff --git a/Lib/random.py b/Lib/random.py index e4a7597af64c00..3ea369b81b3e50 100644 --- a/Lib/random.py +++ b/Lib/random.py @@ -55,7 +55,6 @@ from bisect import bisect as _bisect import os as _os import _random -import types try: # hashlib is pretty heavy to load, try lean internal module first @@ -155,7 +154,7 @@ def seed(self, a=None, version=2): a += _sha512(a).digest() a = int.from_bytes(a, 'big') - elif not isinstance(a, (types.NoneType, int, float, str, bytes, bytearray)): + elif not isinstance(a, (type(None), int, float, str, bytes, bytearray)): _warn('Seeding based on hashing is deprecated\n' 'since Python 3.9 and will be removed in a subsequent ' 'version. The only \n' diff --git a/Lib/runpy.py b/Lib/runpy.py index c27c5bc9959857..7e1e1ac5dde2df 100644 --- a/Lib/runpy.py +++ b/Lib/runpy.py @@ -261,7 +261,7 @@ def run_path(path_name, init_globals=None, run_name=None): if type(importer).__module__ == 'imp': if type(importer).__name__ == 'NullImporter': is_NullImporter = True - if isinstance(importer, types.NoneType) or is_NullImporter: + if isinstance(importer, type(None)) or is_NullImporter: # Not a valid sys.path entry, so run the code directly # execfile() doesn't help as we want to allow compiled files code, fname = _get_code_from_file(run_name, path_name) diff --git a/Lib/sqlite3/test/userfunctions.py b/Lib/sqlite3/test/userfunctions.py index 27b429ce84225f..c11c82e1275778 100644 --- a/Lib/sqlite3/test/userfunctions.py +++ b/Lib/sqlite3/test/userfunctions.py @@ -21,7 +21,6 @@ # misrepresented as being the original software. # 3. This notice may not be removed or altered from any source distribution. -import types import unittest import unittest.mock import sqlite3 as sqlite @@ -50,7 +49,7 @@ def func_isint(v): def func_isfloat(v): return type(v) is float def func_isnone(v): - return type(v) is types.NoneType + return type(v) is type(None) def func_isblob(v): return isinstance(v, (bytes, memoryview)) def func_islonglong(v): @@ -108,7 +107,7 @@ def __init__(self): self.val = None def step(self, whichType, val): - theType = {"str": str, "int": int, "float": float, "None": types.NoneType, + theType = {"str": str, "int": int, "float": float, "None": type(None), "blob": bytes} self.val = int(theType[whichType] is type(val)) @@ -120,7 +119,7 @@ def __init__(self): self.val = 0 def step(self, whichType, *vals): - theType = {"str": str, "int": int, "float": float, "None": types.NoneType, + theType = {"str": str, "int": int, "float": float, "None": type(None), "blob": bytes} for val in vals: self.val += int(theType[whichType] is type(val)) @@ -212,7 +211,7 @@ def CheckFuncReturnNull(self): cur = self.con.cursor() cur.execute("select returnnull()") val = cur.fetchone()[0] - self.assertEqual(type(val), types.NoneType) + self.assertEqual(type(val), type(None)) self.assertEqual(val, None) def CheckFuncReturnBlob(self): diff --git a/Lib/test/test_dataclasses.py b/Lib/test/test_dataclasses.py index 8005f4f361c4b7..b20103bdce51cb 100644 --- a/Lib/test/test_dataclasses.py +++ b/Lib/test/test_dataclasses.py @@ -8,7 +8,6 @@ import inspect import builtins import unittest -import types from unittest.mock import Mock from typing import ClassVar, Any, List, Union, Tuple, Dict, Generic, TypeVar, Optional from typing import get_type_hints @@ -2027,7 +2026,7 @@ class C: def test_docstring_one_field_with_default_none(self): @dataclass class C: - x: Union[int, types.NoneType] = None + x: Union[int, type(None)] = None self.assertDocStrEqual(C.__doc__, "C(x:Optional[int]=None)") @@ -2956,7 +2955,7 @@ def test_text_annotations(self): self.assertEqual( get_type_hints(dataclass_textanno.Bar.__init__), {'foo': dataclass_textanno.Foo, - 'return': types.NoneType}) + 'return': type(None)}) class TestMakeDataclass(unittest.TestCase): diff --git a/Lib/test/test_descr.py b/Lib/test/test_descr.py index 0d2e402f53ae77..307416c3300ae3 100644 --- a/Lib/test/test_descr.py +++ b/Lib/test/test_descr.py @@ -3260,7 +3260,7 @@ class Int(int): __slots__ = [] cant(2, bool) o = object() cant(o, type(1)) - cant(o, types.NoneType) + cant(o, type(None)) del o class G(object): __slots__ = ["a", "b"] @@ -4000,35 +4000,35 @@ class D(C): def test_unsubclassable_types(self): with self.assertRaises(TypeError): - class X(types.NoneType): + class X(type(None)): pass with self.assertRaises(TypeError): - class X(object, types.NoneType): + class X(object, type(None)): pass with self.assertRaises(TypeError): - class X(types.NoneType, object): + class X(type(None), object): pass class O(object): pass with self.assertRaises(TypeError): - class X(O, types.NoneType): + class X(O, type(None)): pass with self.assertRaises(TypeError): - class X(types.NoneType, O): + class X(type(None), O): pass class X(object): pass with self.assertRaises(TypeError): - X.__bases__ = types.NoneType, + X.__bases__ = type(None), with self.assertRaises(TypeError): - X.__bases__ = object, types.NoneType + X.__bases__ = object, type(None) with self.assertRaises(TypeError): - X.__bases__ = types.NoneType, object + X.__bases__ = type(None), object with self.assertRaises(TypeError): - X.__bases__ = O, types.NoneType + X.__bases__ = O, type(None) with self.assertRaises(TypeError): - X.__bases__ = types.NoneType, O + X.__bases__ = type(None), O def test_mutable_bases_with_failing_mro(self): # Testing mutable bases with failing mro... diff --git a/Lib/test/test_getargs2.py b/Lib/test/test_getargs2.py index 1803adc0b8ab8e..09560197913059 100644 --- a/Lib/test/test_getargs2.py +++ b/Lib/test/test_getargs2.py @@ -2,7 +2,6 @@ import math import string import sys -import types from test import support from test.support import import_helper # Skip this test if the _testcapi module isn't available. @@ -568,11 +567,11 @@ def test_args(self): ret = get_args() self.assertIn(ret, ((), None)) - self.assertIn(type(ret), (tuple, types.NoneType)) + self.assertIn(type(ret), (tuple, type(None))) ret = get_args(*()) self.assertIn(ret, ((), None)) - self.assertIn(type(ret), (tuple, types.NoneType)) + self.assertIn(type(ret), (tuple, type(None))) def test_tuple(self): from _testcapi import getargs_tuple @@ -606,11 +605,11 @@ def test_kwargs(self): ret = get_kwargs() self.assertIn(ret, ({}, None)) - self.assertIn(type(ret), (dict, types.NoneType)) + self.assertIn(type(ret), (dict, type(None))) ret = get_kwargs(**{}) self.assertIn(ret, ({}, None)) - self.assertIn(type(ret), (dict, types.NoneType)) + self.assertIn(type(ret), (dict, type(None))) def test_positional_args(self): # using all positional args diff --git a/Lib/test/test_nntplib.py b/Lib/test/test_nntplib.py index 4a21e96033f032..b11c19c84d3fb1 100644 --- a/Lib/test/test_nntplib.py +++ b/Lib/test/test_nntplib.py @@ -9,7 +9,6 @@ import os.path import re import threading -import types from test import support from test.support import socket_helper @@ -127,7 +126,7 @@ def _check_art_dict(self, art_dict): "references", ":bytes", ":lines"} ) for v in art_dict.values(): - self.assertIsInstance(v, (str, types.NoneType)) + self.assertIsInstance(v, (str, type(None))) def test_xover(self): resp, count, first, last, name = self.server.group(self.GROUP_NAME) diff --git a/Lib/test/test_pwd.py b/Lib/test/test_pwd.py index 67602147660c56..f8f12571ca90e0 100644 --- a/Lib/test/test_pwd.py +++ b/Lib/test/test_pwd.py @@ -1,6 +1,5 @@ import sys import unittest -import types from test.support import import_helper pwd = import_helper.import_module('pwd') @@ -22,7 +21,7 @@ def test_values(self): self.assertEqual(e[3], e.pw_gid) self.assertIsInstance(e.pw_gid, int) self.assertEqual(e[4], e.pw_gecos) - self.assertIn(type(e.pw_gecos), (str, types.NoneType)) + self.assertIn(type(e.pw_gecos), (str, type(None))) self.assertEqual(e[5], e.pw_dir) self.assertIsInstance(e.pw_dir, str) self.assertEqual(e[6], e.pw_shell) diff --git a/Lib/test/test_ssl.py b/Lib/test/test_ssl.py index 60f52c1a9308ca..26eec969a82e0d 100644 --- a/Lib/test/test_ssl.py +++ b/Lib/test/test_ssl.py @@ -25,7 +25,6 @@ import platform import sysconfig import functools -import types try: import ctypes except ImportError: @@ -972,7 +971,7 @@ def test_asn1object(self): self.assertIsInstance(obj.nid, int) self.assertIsInstance(obj.shortname, str) self.assertIsInstance(obj.longname, str) - self.assertIsInstance(obj.oid, (str, types.NoneType)) + self.assertIsInstance(obj.oid, (str, type(None))) val = ssl._ASN1Object.fromname('TLS Web Server Authentication') self.assertEqual(val, expected) diff --git a/Lib/test/test_statistics.py b/Lib/test/test_statistics.py index a6695f1318ce3f..997110732a1765 100644 --- a/Lib/test/test_statistics.py +++ b/Lib/test/test_statistics.py @@ -14,7 +14,6 @@ import random import sys import unittest -import types from test import support from test.support import import_helper @@ -938,7 +937,7 @@ def test_float(self): self.check_type_coercions(float) def test_non_numeric_types(self): - for bad_type in (str, list, types.NoneType, tuple, dict): + for bad_type in (str, list, type(None), tuple, dict): for good_type in (int, float, Fraction, Decimal): self.assertCoerceRaises(good_type, bad_type) diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index 3465cf9fb0e4ce..42aa430c5e107e 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -2845,7 +2845,7 @@ def test_get_type_hints_classes(self): self.assertEqual(gth(ann_module.S), {'x': str, 'y': str}) self.assertEqual(gth(ann_module.foo), {'x': int}) self.assertEqual(gth(NoneAndForward), - {'parent': NoneAndForward, 'meaning': types.NoneType}) + {'parent': NoneAndForward, 'meaning': type(None)}) self.assertEqual(gth(HasForeignBaseClass), {'some_xrepr': XRepr, 'other_a': mod_generics_cache.A, 'some_b': mod_generics_cache.B}) @@ -2885,7 +2885,7 @@ def testf(x, y): ... testf.__annotations__['x'] = 'int' self.assertEqual(gth(testf), {'x': int}) def testg(x: None): ... - self.assertEqual(gth(testg), {'x': types.NoneType}) + self.assertEqual(gth(testg), {'x': type(None)}) def test_get_type_hints_for_object_with_annotations(self): class A: ... diff --git a/Lib/tkinter/__init__.py b/Lib/tkinter/__init__.py index 0a5988dd61cecc..1067ab6a8b8a1d 100644 --- a/Lib/tkinter/__init__.py +++ b/Lib/tkinter/__init__.py @@ -102,7 +102,7 @@ def _cnfmerge(cnfs): """Internal function.""" if isinstance(cnfs, dict): return cnfs - elif isinstance(cnfs, (types.NoneType, str)): + elif isinstance(cnfs, (type(None), str)): return cnfs else: cnf = {} diff --git a/Lib/tkinter/ttk.py b/Lib/tkinter/ttk.py index 3b32b1b95994d4..c7c71cd5a559cf 100644 --- a/Lib/tkinter/ttk.py +++ b/Lib/tkinter/ttk.py @@ -25,7 +25,6 @@ # functions "tclobjs_to_py", "setup_master"] -import types import tkinter from tkinter import _flatten, _join, _stringify, _splitdict @@ -1086,7 +1085,7 @@ def configure(self, cnf=None, **kw): Setting a value for any of the "from", "from_" or "to" options generates a <> event.""" retval = Widget.configure(self, cnf, **kw) - if not isinstance(cnf, (types.NoneType, str)): + if not isinstance(cnf, (type(None), str)): kw.update(cnf) if any(['from' in kw, 'from_' in kw, 'to' in kw]): self.event_generate('<>') diff --git a/Lib/typing.py b/Lib/typing.py index 356cab9cc3b0b8..8c61bd8e084a85 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -121,7 +121,7 @@ def _type_check(arg, msg, is_argument=True): """Check that the argument is a type, and return it (internal helper). - As a special case, accept None and return types.NoneType instead. Also wrap strings + As a special case, accept None and return type(None) instead. Also wrap strings into ForwardRef instances. Consider several corner cases, for example plain special forms like Union are not valid, while Union[int, str] is OK, etc. The msg argument is a human-readable error message, e.g:: @@ -135,7 +135,7 @@ def _type_check(arg, msg, is_argument=True): invalid_generic_forms = invalid_generic_forms + (ClassVar, Final) if arg is None: - return types.NoneType + return type(None) if isinstance(arg, str): return ForwardRef(arg) if (isinstance(arg, _GenericAlias) and @@ -392,7 +392,7 @@ def Union(self, parameters): To define a union, use e.g. Union[int, str]. Details: - The arguments must be types and there must be at least one. - None as an argument is a special case and is replaced by - types.NoneType. + type(None). - Unions of unions are flattened, e.g.:: Union[Union[int, str], float] == Union[int, str, float] @@ -430,7 +430,7 @@ def Optional(self, parameters): Optional[X] is equivalent to Union[X, None]. """ arg = _type_check(parameters, f"{self} requires a single type.") - return Union[arg, types.NoneType] + return Union[arg, type(None)] @_SpecialForm def Literal(self, parameters): @@ -889,9 +889,9 @@ def __hash__(self): def __repr__(self): args = self.__args__ if len(args) == 2: - if args[0] is types.NoneType: + if args[0] is type(None): return f'typing.Optional[{_type_repr(args[1])}]' - elif args[1] is types.NoneType: + elif args[1] is type(None): return f'typing.Optional[{_type_repr(args[0])}]' return super().__repr__() @@ -1374,7 +1374,7 @@ def get_type_hints(obj, globalns=None, localns=None, include_extras=False): ann = base.__dict__.get('__annotations__', {}) for name, value in ann.items(): if value is None: - value = types.NoneType + value = type(None) if isinstance(value, str): value = ForwardRef(value, is_argument=False) value = _eval_type(value, base_globals, localns) @@ -1406,7 +1406,7 @@ def get_type_hints(obj, globalns=None, localns=None, include_extras=False): hints = dict(hints) for name, value in hints.items(): if value is None: - value = types.NoneType + value = type(None) if isinstance(value, str): value = ForwardRef(value) value = _eval_type(value, globalns, localns) diff --git a/Lib/unittest/test/testmock/testhelpers.py b/Lib/unittest/test/testmock/testhelpers.py index 10e7c35f0ae6ea..9e7ec5d62d5da2 100644 --- a/Lib/unittest/test/testmock/testhelpers.py +++ b/Lib/unittest/test/testmock/testhelpers.py @@ -863,7 +863,7 @@ class Foo(object): mock = create_autospec(Foo) none = mock.bar - self.assertNotIsInstance(none, types.NoneType) + self.assertNotIsInstance(none, type(None)) none.foo() none.foo.assert_called_once_with() diff --git a/Lib/xmlrpc/client.py b/Lib/xmlrpc/client.py index 575d67a0b3ff0f..d15d60d2937a82 100644 --- a/Lib/xmlrpc/client.py +++ b/Lib/xmlrpc/client.py @@ -138,7 +138,6 @@ from xml.parsers import expat import errno from io import BytesIO -import types try: import gzip except ImportError: @@ -534,7 +533,7 @@ def dump_nil (self, value, write): if not self.allow_none: raise TypeError("cannot marshal None unless allow_none is enabled") write("") - dispatch[types.NoneType] = dump_nil + dispatch[type(None)] = dump_nil def dump_bool(self, value, write): write("") From 23ed559738432aae3e2cca47636c75f15abc341a Mon Sep 17 00:00:00 2001 From: Bas van Beek Date: Tue, 22 Sep 2020 16:28:25 +0200 Subject: [PATCH 13/13] Reworded parts of the `constants` documentation Addresses https://github.com/python/cpython/pull/22336#discussion_r492478512, https://github.com/python/cpython/pull/22336#discussion_r492479743 & https://github.com/python/cpython/pull/22336#discussion_r492480008 --- Doc/library/constants.rst | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/Doc/library/constants.rst b/Doc/library/constants.rst index 11bd0d2b4c89eb..38dd552a0363ac 100644 --- a/Doc/library/constants.rst +++ b/Doc/library/constants.rst @@ -19,20 +19,21 @@ A small number of constants live in the built-in namespace. They are: .. data:: None - The sole value of the type :data:`types.NoneType`. ``None`` is frequently used to - represent the absence of a value, as when default arguments are not passed to a - function. Assignments to ``None`` are illegal and raise a :exc:`SyntaxError`. + An object frequently used to represent the absence of a value, as when + default arguments are not passed to a function. Assignments to ``None`` + are illegal and raise a :exc:`SyntaxError`. + ``None`` is the sole instance of the :data:`NoneType` type. .. data:: NotImplemented - Sole value of the type :data:`types.NotImplementedType` and a - special value which should be returned by the binary special methods + A special value which should be returned by the binary special methods (e.g. :meth:`__eq__`, :meth:`__lt__`, :meth:`__add__`, :meth:`__rsub__`, etc.) to indicate that the operation is not implemented with respect to the other type; may be returned by the in-place binary special methods (e.g. :meth:`__imul__`, :meth:`__iand__`, etc.) for the same purpose. It should not be evaluated in a boolean context. + ``NotImplemented`` is the sole instance of the :data:`types.NotImplementedType` type. .. note:: @@ -60,9 +61,9 @@ A small number of constants live in the built-in namespace. They are: .. index:: single: ...; ellipsis literal .. data:: Ellipsis - The same as the ellipsis literal "``...``" and sole value of the type - :data:`types.EllipsisType`. Special value used mostly in conjunction + The same as the ellipsis literal "``...``". Special value used mostly in conjunction with extended slicing syntax for user-defined container data types. + ``Ellipsis`` is the sole instance of the :data:`types.EllipsisType` type. .. data:: __debug__ pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy