From 0c12774adb2d8e7b72f34d0c8aa0a22d51740e75 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Fri, 4 Feb 2022 15:21:03 +0800 Subject: [PATCH 01/11] Remove kwargs syntax for TypedDict --- Doc/library/typing.rst | 8 +++++--- Lib/test/test_typing.py | 31 ++----------------------------- Lib/typing.py | 10 ++-------- 3 files changed, 9 insertions(+), 40 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 9007c0daf59a4d..d8162a8c0cc9bb 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1388,10 +1388,9 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__total__``, ``Point2D.__required_keys__``, and ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not - support :pep:`526`, ``TypedDict`` supports two additional equivalent - syntactic forms:: + support :pep:`526`, ``TypedDict`` supports an additional equivalent + syntactic form:: - Point2D = TypedDict('Point2D', x=int, y=int, label=str) Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) By default, all keys must be present in a ``TypedDict``. It is possible to @@ -1402,6 +1401,9 @@ These are not used in annotations. They are building blocks for declaring types. x: int y: int + # Alternative syntax + Point2D = TypedDict('Point2D', {'x': int, 'y': int}, total=False) + This means that a ``Point2D`` ``TypedDict`` can have any of the keys omitted. A type checker is only expected to support a literal ``False`` or ``True`` as the value of the ``total`` argument. ``True`` is the default, diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index 85f74064458f2d..8db0acf38a2a85 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -4299,33 +4299,6 @@ def test_basics_functional_syntax(self): self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) self.assertEqual(Emp.__total__, True) - def test_basics_keywords_syntax(self): - Emp = TypedDict('Emp', name=str, id=int) - self.assertIsSubclass(Emp, dict) - self.assertIsSubclass(Emp, typing.MutableMapping) - self.assertNotIsSubclass(Emp, collections.abc.Sequence) - jim = Emp(name='Jim', id=1) - self.assertIs(type(jim), dict) - self.assertEqual(jim['name'], 'Jim') - self.assertEqual(jim['id'], 1) - self.assertEqual(Emp.__name__, 'Emp') - self.assertEqual(Emp.__module__, __name__) - self.assertEqual(Emp.__bases__, (dict,)) - self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) - self.assertEqual(Emp.__total__, True) - - def test_typeddict_special_keyword_names(self): - TD = TypedDict("TD", cls=type, self=object, typename=str, _typename=int, fields=list, _fields=dict) - self.assertEqual(TD.__name__, 'TD') - self.assertEqual(TD.__annotations__, {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) - a = TD(cls=str, self=42, typename='foo', _typename=53, fields=[('bar', tuple)], _fields={'baz', set}) - self.assertEqual(a['cls'], str) - self.assertEqual(a['self'], 42) - self.assertEqual(a['typename'], 'foo') - self.assertEqual(a['_typename'], 53) - self.assertEqual(a['fields'], [('bar', tuple)]) - self.assertEqual(a['_fields'], {'baz', set}) - def test_typeddict_create_errors(self): with self.assertRaises(TypeError): TypedDict.__new__() @@ -4371,7 +4344,7 @@ def test_py36_class_syntax_usage(self): def test_pickle(self): global EmpD # pickle wants to reference the class by name - EmpD = TypedDict('EmpD', name=str, id=int) + EmpD = TypedDict('EmpD', {'name': str, 'id': int}) jane = EmpD({'name': 'jane', 'id': 37}) for proto in range(pickle.HIGHEST_PROTOCOL + 1): z = pickle.dumps(jane, proto) @@ -4383,7 +4356,7 @@ def test_pickle(self): self.assertEqual(EmpDnew({'name': 'jane', 'id': 37}), jane) def test_optional(self): - EmpD = TypedDict('EmpD', name=str, id=int) + EmpD = TypedDict('EmpD', {'name': str, 'id': int}) self.assertEqual(typing.Optional[EmpD], typing.Union[None, EmpD]) self.assertNotEqual(typing.List[EmpD], typing.Tuple[EmpD]) diff --git a/Lib/typing.py b/Lib/typing.py index 0cf9755022e9b8..8239149c2fac6d 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -2378,7 +2378,7 @@ def __subclasscheck__(cls, other): __instancecheck__ = __subclasscheck__ -def TypedDict(typename, fields=None, /, *, total=True, **kwargs): +def TypedDict(typename, fields=None, /, *, total=True): """A simple typed namespace. At runtime it is equivalent to a plain dict. TypedDict creates a dictionary type that expects all of its @@ -2399,9 +2399,8 @@ class Point2D(TypedDict): The type info can be accessed via the Point2D.__annotations__ dict, and the Point2D.__required_keys__ and Point2D.__optional_keys__ frozensets. - TypedDict supports two additional equivalent forms:: + TypedDict supports an additional equivalent form:: - Point2D = TypedDict('Point2D', x=int, y=int, label=str) Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) By default, all keys must be present in a TypedDict. It is possible @@ -2420,11 +2419,6 @@ class body be required. The class syntax is only supported in Python 3.6+, while two other syntax forms work for Python 2.7 and 3.2+ """ - if fields is None: - fields = kwargs - elif kwargs: - raise TypeError("TypedDict takes either a dict or keyword arguments," - " but not both") ns = {'__annotations__': dict(fields)} module = _caller() From f3588ac8ba55ec7d629eac36b7f504d2ba9d3c3b Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Tue, 8 Feb 2022 01:58:41 +0800 Subject: [PATCH 02/11] Add deprecation flag and warning --- Doc/library/typing.rst | 9 +++++++-- Lib/test/test_typing.py | 28 ++++++++++++++++++++++++++++ Lib/typing.py | 14 +++++++++++++- 3 files changed, 48 insertions(+), 3 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index d8162a8c0cc9bb..938cf10874b05a 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1388,10 +1388,15 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__total__``, ``Point2D.__required_keys__``, and ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not - support :pep:`526`, ``TypedDict`` supports an additional equivalent - syntactic form:: + support :pep:`526`, ``TypedDict`` supports two additional equivalent + syntactic forms:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) + Point2D = TypedDict('Point2D', x=int, y=int, label=str) + + .. deprecated-removed:: 3.11 3.13 + The keyword arguments syntax is deprecated in 3.11 and will be removed + in 3.13. Currently it might not be supported by typecheckers like ``mypy``. By default, all keys must be present in a ``TypedDict``. It is possible to override this by specifying totality. diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index 8db0acf38a2a85..1ba31ad397606e 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -4299,6 +4299,34 @@ def test_basics_functional_syntax(self): self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) self.assertEqual(Emp.__total__, True) + def test_basics_keywords_syntax(self): + with self.assertWarns(DeprecationWarning): + Emp = TypedDict('Emp', name=str, id=int) + self.assertIsSubclass(Emp, dict) + self.assertIsSubclass(Emp, typing.MutableMapping) + self.assertNotIsSubclass(Emp, collections.abc.Sequence) + jim = Emp(name='Jim', id=1) + self.assertIs(type(jim), dict) + self.assertEqual(jim['name'], 'Jim') + self.assertEqual(jim['id'], 1) + self.assertEqual(Emp.__name__, 'Emp') + self.assertEqual(Emp.__module__, __name__) + self.assertEqual(Emp.__bases__, (dict,)) + self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) + self.assertEqual(Emp.__total__, True) + + def test_typeddict_special_keyword_names(self): + TD = TypedDict("TD", {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) + self.assertEqual(TD.__name__, 'TD') + self.assertEqual(TD.__annotations__, {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) + a = TD(cls=str, self=42, typename='foo', _typename=53, fields=[('bar', tuple)], _fields={'baz', set}) + self.assertEqual(a['cls'], str) + self.assertEqual(a['self'], 42) + self.assertEqual(a['typename'], 'foo') + self.assertEqual(a['_typename'], 53) + self.assertEqual(a['fields'], [('bar', tuple)]) + self.assertEqual(a['_fields'], {'baz', set}) + def test_typeddict_create_errors(self): with self.assertRaises(TypeError): TypedDict.__new__() diff --git a/Lib/typing.py b/Lib/typing.py index 8239149c2fac6d..df6c2aabe1c96a 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -2378,7 +2378,7 @@ def __subclasscheck__(cls, other): __instancecheck__ = __subclasscheck__ -def TypedDict(typename, fields=None, /, *, total=True): +def TypedDict(typename, fields=None, /, *, total=True, **kwargs): """A simple typed namespace. At runtime it is equivalent to a plain dict. TypedDict creates a dictionary type that expects all of its @@ -2419,6 +2419,18 @@ class body be required. The class syntax is only supported in Python 3.6+, while two other syntax forms work for Python 2.7 and 3.2+ """ + if fields is None: + fields = kwargs + elif kwargs: + raise TypeError("TypedDict takes either a dict or keyword arguments," + " but not both") + if kwargs: + warnings.warn( + "The kwargs-based syntax for TypedDict definition is deprecated " + " in Python 3.11 and will be removed in Python 3.13.", + DeprecationWarning, + stacklevel=2, + ) ns = {'__annotations__': dict(fields)} module = _caller() From 4d988a8570ee8bf09a2b94e53fedb4233d9b5611 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Tue, 8 Feb 2022 16:43:23 +0800 Subject: [PATCH 03/11] Add blurb and address reviews --- Doc/library/typing.rst | 8 ++++++-- Lib/typing.py | 4 ++-- .../next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst | 1 + 3 files changed, 9 insertions(+), 4 deletions(-) create mode 100644 Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 938cf10874b05a..ecc19b940f9574 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1389,14 +1389,18 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not support :pep:`526`, ``TypedDict`` supports two additional equivalent - syntactic forms:: + syntactic forms. + Using dict as the second argument:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) + + Using keyword arguments:: + Point2D = TypedDict('Point2D', x=int, y=int, label=str) .. deprecated-removed:: 3.11 3.13 The keyword arguments syntax is deprecated in 3.11 and will be removed - in 3.13. Currently it might not be supported by typecheckers like ``mypy``. + in 3.13. Currently it might not be supported by typecheckers. By default, all keys must be present in a ``TypedDict``. It is possible to override this by specifying totality. diff --git a/Lib/typing.py b/Lib/typing.py index df6c2aabe1c96a..5cfbd9bbdfbbb1 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -2416,8 +2416,8 @@ class point2D(TypedDict, total=False): the total argument. True is the default, and makes all items defined in the class body be required. - The class syntax is only supported in Python 3.6+, while two other - syntax forms work for Python 2.7 and 3.2+ + The class syntax is only supported in Python 3.6+, while the other + syntax form works for Python 2.7 and 3.2+ """ if fields is None: fields = kwargs diff --git a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst new file mode 100644 index 00000000000000..fce4136864fdf7 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst @@ -0,0 +1 @@ +Remove kwargs-based syntax for TypedDict definition From f21c30ae3bfd63e9a3837f9d831f6802ae6ea50d Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Tue, 8 Feb 2022 23:46:28 +0800 Subject: [PATCH 04/11] Change docs Co-authored-by: AlexWaygood --- Doc/library/typing.rst | 10 +++++----- Lib/test/test_typing.py | 24 ++++++++++++------------ Lib/typing.py | 5 +++-- 3 files changed, 20 insertions(+), 19 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index ecc19b940f9574..0c13d993b3f65e 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1389,18 +1389,18 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not support :pep:`526`, ``TypedDict`` supports two additional equivalent - syntactic forms. - Using dict as the second argument:: + syntactic forms. Firstly, using a literal :class:`dict` as the + second argument:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) - Using keyword arguments:: + Secondly, using keyword arguments:: Point2D = TypedDict('Point2D', x=int, y=int, label=str) .. deprecated-removed:: 3.11 3.13 - The keyword arguments syntax is deprecated in 3.11 and will be removed - in 3.13. Currently it might not be supported by typecheckers. + The keyword-argument syntax is deprecated in 3.11 and will be removed + in 3.13. It may also be unsupported by third-party type-checking tools. By default, all keys must be present in a ``TypedDict``. It is possible to override this by specifying totality. diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index 1ba31ad397606e..c15e873cab6cf6 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -4302,18 +4302,18 @@ def test_basics_functional_syntax(self): def test_basics_keywords_syntax(self): with self.assertWarns(DeprecationWarning): Emp = TypedDict('Emp', name=str, id=int) - self.assertIsSubclass(Emp, dict) - self.assertIsSubclass(Emp, typing.MutableMapping) - self.assertNotIsSubclass(Emp, collections.abc.Sequence) - jim = Emp(name='Jim', id=1) - self.assertIs(type(jim), dict) - self.assertEqual(jim['name'], 'Jim') - self.assertEqual(jim['id'], 1) - self.assertEqual(Emp.__name__, 'Emp') - self.assertEqual(Emp.__module__, __name__) - self.assertEqual(Emp.__bases__, (dict,)) - self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) - self.assertEqual(Emp.__total__, True) + self.assertIsSubclass(Emp, dict) + self.assertIsSubclass(Emp, typing.MutableMapping) + self.assertNotIsSubclass(Emp, collections.abc.Sequence) + jim = Emp(name='Jim', id=1) + self.assertIs(type(jim), dict) + self.assertEqual(jim['name'], 'Jim') + self.assertEqual(jim['id'], 1) + self.assertEqual(Emp.__name__, 'Emp') + self.assertEqual(Emp.__module__, __name__) + self.assertEqual(Emp.__bases__, (dict,)) + self.assertEqual(Emp.__annotations__, {'name': str, 'id': int}) + self.assertEqual(Emp.__total__, True) def test_typeddict_special_keyword_names(self): TD = TypedDict("TD", {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) diff --git a/Lib/typing.py b/Lib/typing.py index 5cfbd9bbdfbbb1..4189771e673a31 100644 --- a/Lib/typing.py +++ b/Lib/typing.py @@ -2426,8 +2426,9 @@ class body be required. " but not both") if kwargs: warnings.warn( - "The kwargs-based syntax for TypedDict definition is deprecated " - " in Python 3.11 and will be removed in Python 3.13.", + "The kwargs-based syntax for TypedDict definitions is deprecated " + "in Python 3.11, will be removed in Python 3.13, and may not be " + "understood by third-party type checkers.", DeprecationWarning, stacklevel=2, ) From 3f60fb0bed883eaf7ea011ebb63982ff450fcb07 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Tue, 8 Feb 2022 23:46:50 +0800 Subject: [PATCH 05/11] Add name --- Misc/ACKS | 1 + .../next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/Misc/ACKS b/Misc/ACKS index 6df339c3e145bf..9dee7992cde05f 100644 --- a/Misc/ACKS +++ b/Misc/ACKS @@ -1976,6 +1976,7 @@ Masayuki Yamamoto Ka-Ping Yee Chi Hsuan Yen Jason Yeo +Jingchen Ye EungJun Yi Bob Yodlowski Danny Yoo diff --git a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst index fce4136864fdf7..1af4dd3997ca5f 100644 --- a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst +++ b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst @@ -1 +1,2 @@ -Remove kwargs-based syntax for TypedDict definition +Deprecate kwargs-based syntax for :class:`typing.TypedDict` definitions. +It was unsupported by type checkers. Patch by Jingchen Ye. \ No newline at end of file From 033cf07be9a90ea17f932c7b6f58df577648b11a Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Wed, 9 Feb 2022 00:26:55 +0800 Subject: [PATCH 06/11] Fix --- Doc/library/typing.rst | 4 ++-- Misc/ACKS | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 0c13d993b3f65e..187747e88581ce 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1393,9 +1393,9 @@ These are not used in annotations. They are building blocks for declaring types. second argument:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) - + Secondly, using keyword arguments:: - + Point2D = TypedDict('Point2D', x=int, y=int, label=str) .. deprecated-removed:: 3.11 3.13 diff --git a/Misc/ACKS b/Misc/ACKS index 9dee7992cde05f..eaaaf7259dc192 100644 --- a/Misc/ACKS +++ b/Misc/ACKS @@ -1973,10 +1973,10 @@ Arnon Yaari Alakshendra Yadav Hirokazu Yamamoto Masayuki Yamamoto +Jingchen Ye Ka-Ping Yee Chi Hsuan Yen Jason Yeo -Jingchen Ye EungJun Yi Bob Yodlowski Danny Yoo From eea168f06ae240e5e4f1716e56489ff24fdd1fba Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Wed, 9 Feb 2022 19:25:43 +0800 Subject: [PATCH 07/11] Modify docs --- Doc/library/typing.rst | 2 +- Lib/test/test_typing.py | 3 ++- .../next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst | 3 ++- 3 files changed, 5 insertions(+), 3 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 187747e88581ce..6784380b6a8822 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1400,7 +1400,7 @@ These are not used in annotations. They are building blocks for declaring types. .. deprecated-removed:: 3.11 3.13 The keyword-argument syntax is deprecated in 3.11 and will be removed - in 3.13. It may also be unsupported by third-party type-checking tools. + in 3.13. It may also be unsupported by static type checkers. By default, all keys must be present in a ``TypedDict``. It is possible to override this by specifying totality. diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py index c15e873cab6cf6..b0754c9500edb9 100644 --- a/Lib/test/test_typing.py +++ b/Lib/test/test_typing.py @@ -4316,7 +4316,8 @@ def test_basics_keywords_syntax(self): self.assertEqual(Emp.__total__, True) def test_typeddict_special_keyword_names(self): - TD = TypedDict("TD", {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) + with self.assertWarns(DeprecationWarning): + TD = TypedDict("TD", cls=type, self=object, typename=str, _typename=int, fields=list, _fields=dict) self.assertEqual(TD.__name__, 'TD') self.assertEqual(TD.__annotations__, {'cls': type, 'self': object, 'typename': str, '_typename': int, 'fields': list, '_fields': dict}) a = TD(cls=str, self=42, typename='foo', _typename=53, fields=[('bar', tuple)], _fields={'baz', set}) diff --git a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst index 1af4dd3997ca5f..d4681633fa9d83 100644 --- a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst +++ b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst @@ -1,2 +1,3 @@ Deprecate kwargs-based syntax for :class:`typing.TypedDict` definitions. -It was unsupported by type checkers. Patch by Jingchen Ye. \ No newline at end of file +It had confusing semantics when specifying totality, and was largely unused. +Patch by Jingchen Ye. \ No newline at end of file From 15a7930fef47f604ca59acbcf6a6670a9a296dc2 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Sun, 13 Feb 2022 15:16:56 +0800 Subject: [PATCH 08/11] Use bullet list --- Doc/library/typing.rst | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 6784380b6a8822..39adfc917802a1 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1388,13 +1388,13 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__total__``, ``Point2D.__required_keys__``, and ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not - support :pep:`526`, ``TypedDict`` supports two additional equivalent - syntactic forms. Firstly, using a literal :class:`dict` as the - second argument:: + support :pep:`526`, ``TypedDict`` can be created using a functional form: + + * Using a literal :class:`dict` as the second argument:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) - Secondly, using keyword arguments:: + * Using keyword arguments:: Point2D = TypedDict('Point2D', x=int, y=int, label=str) From b9badea8616805fdc8527f3e6fb2e29ea87ecb64 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Sun, 13 Feb 2022 18:09:41 +0800 Subject: [PATCH 09/11] Fix --- Doc/library/typing.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 39adfc917802a1..9adc88eed5bb25 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1389,7 +1389,7 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not support :pep:`526`, ``TypedDict`` can be created using a functional form: - + * Using a literal :class:`dict` as the second argument:: Point2D = TypedDict('Point2D', {'x': int, 'y': int, 'label': str}) From a6a870c6cc6a1a6d6663e1d7389d37d61d5da554 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <97littleleaf11@gmail.com> Date: Sun, 13 Feb 2022 20:05:08 +0800 Subject: [PATCH 10/11] Fix --- .../next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst index d4681633fa9d83..d13d9421e748b8 100644 --- a/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst +++ b/Misc/NEWS.d/next/Library/2022-02-08-16-42-20.bpo-46066.m32Hl0.rst @@ -1,3 +1,3 @@ Deprecate kwargs-based syntax for :class:`typing.TypedDict` definitions. It had confusing semantics when specifying totality, and was largely unused. -Patch by Jingchen Ye. \ No newline at end of file +Patch by Jingchen Ye. From 8b113dd3b075674e1e4d05f4eead7d4b15c62e05 Mon Sep 17 00:00:00 2001 From: 97littleleaf11 <11172084+97littleleaf11@users.noreply.github.com> Date: Tue, 15 Feb 2022 15:37:44 +0800 Subject: [PATCH 11/11] reverse --- Doc/library/typing.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst index 9adc88eed5bb25..fe0f475a492cd7 100644 --- a/Doc/library/typing.rst +++ b/Doc/library/typing.rst @@ -1388,7 +1388,8 @@ These are not used in annotations. They are building blocks for declaring types. ``Point2D.__total__``, ``Point2D.__required_keys__``, and ``Point2D.__optional_keys__``. To allow using this feature with older versions of Python that do not - support :pep:`526`, ``TypedDict`` can be created using a functional form: + support :pep:`526`, ``TypedDict`` supports two additional equivalent + syntactic forms: * Using a literal :class:`dict` as the second argument:: 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