https://github.com/python/cpython/commit/56e4a417ce170e5c538ce9aafccf3333e7bf7492
commit: 56e4a417ce170e5c538ce9aafccf3333e7bf7492
branch: main
author: Stanislav Terliakov <[email protected]>
committer: AlexWaygood <[email protected]>
date: 2024-09-06T17:41:06+01:00
summary:
gh-123523: Rework typing documentation for generators and coroutines, and link
to it from `collections.abc` docs (#123544)
files:
M Doc/library/collections.abc.rst
M Doc/library/typing.rst
diff --git a/Doc/library/collections.abc.rst b/Doc/library/collections.abc.rst
index a63a55caa0f66d..b77a36393b2769 100644
--- a/Doc/library/collections.abc.rst
+++ b/Doc/library/collections.abc.rst
@@ -213,6 +213,9 @@ Collections Abstract Base Classes -- Detailed Descriptions
ABC for classes that provide the :meth:`~object.__call__` method.
+ See :ref:`annotating-callables` for details on how to use
+ :class:`!Callable` in type annotations.
+
.. class:: Iterable
ABC for classes that provide the :meth:`~container.__iter__` method.
@@ -250,6 +253,9 @@ Collections Abstract Base Classes -- Detailed Descriptions
:meth:`~generator.send`,
:meth:`~generator.throw` and :meth:`~generator.close` methods.
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`!Generator` in type annotations.
+
.. versionadded:: 3.5
.. class:: Sequence
@@ -321,6 +327,11 @@ Collections Abstract Base Classes -- Detailed Descriptions
Using ``isinstance(gencoro, Coroutine)`` for them will return ``False``.
Use :func:`inspect.isawaitable` to detect them.
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`!Coroutine` in type annotations.
+ The variance and order of type parameters correspond to those of
+ :class:`Generator`.
+
.. versionadded:: 3.5
.. class:: AsyncIterable
@@ -342,6 +353,9 @@ Collections Abstract Base Classes -- Detailed Descriptions
ABC for :term:`asynchronous generator` classes that implement the protocol
defined in :pep:`525` and :pep:`492`.
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`!AsyncGenerator` in type annotations.
+
.. versionadded:: 3.6
.. class:: Buffer
diff --git a/Doc/library/typing.rst b/Doc/library/typing.rst
index 7d1d317b9f8f8a..f8b533a5fc87aa 100644
--- a/Doc/library/typing.rst
+++ b/Doc/library/typing.rst
@@ -208,7 +208,7 @@ Annotating callable objects
===========================
Functions -- or other :term:`callable` objects -- can be annotated using
-:class:`collections.abc.Callable` or :data:`typing.Callable`.
+:class:`collections.abc.Callable` or deprecated :data:`typing.Callable`.
``Callable[[int], str]`` signifies a function that takes a single parameter
of type :class:`int` and returns a :class:`str`.
@@ -401,7 +401,7 @@ The type of class objects
=========================
A variable annotated with ``C`` may accept a value of type ``C``. In
-contrast, a variable annotated with ``type[C]`` (or
+contrast, a variable annotated with ``type[C]`` (or deprecated
:class:`typing.Type[C] <Type>`) may accept values that are classes
themselves -- specifically, it will accept the *class object* of ``C``. For
example::
@@ -441,6 +441,87 @@ For example::
``type[Any]`` is equivalent to :class:`type`, which is the root of Python's
:ref:`metaclass hierarchy <metaclasses>`.
+
+.. _annotating-generators-and-coroutines:
+
+Annotating generators and coroutines
+====================================
+
+A generator can be annotated using the generic type
+:class:`Generator[YieldType, SendType, ReturnType]
<collections.abc.Generator>`.
+For example::
+
+ def echo_round() -> Generator[int, float, str]:
+ sent = yield 0
+ while sent >= 0:
+ sent = yield round(sent)
+ return 'Done'
+
+Note that unlike many other generic classes in the standard library,
+the ``SendType`` of :class:`~collections.abc.Generator` behaves
+contravariantly, not covariantly or invariantly.
+
+The ``SendType`` and ``ReturnType`` parameters default to :const:`!None`::
+
+ def infinite_stream(start: int) -> Generator[int]:
+ while True:
+ yield start
+ start += 1
+
+It is also possible to set these types explicitly::
+
+ def infinite_stream(start: int) -> Generator[int, None, None]:
+ while True:
+ yield start
+ start += 1
+
+Simple generators that only ever yield values can also be annotated
+as having a return type of either
+:class:`Iterable[YieldType] <collections.abc.Iterable>`
+or :class:`Iterator[YieldType] <collections.abc.Iterator>`::
+
+ def infinite_stream(start: int) -> Iterator[int]:
+ while True:
+ yield start
+ start += 1
+
+Async generators are handled in a similar fashion, but don't
+expect a ``ReturnType`` type argument
+(:class:`AsyncGenerator[YieldType, SendType]
<collections.abc.AsyncGenerator>`).
+The ``SendType`` argument defaults to :const:`!None`, so the following
definitions
+are equivalent::
+
+ async def infinite_stream(start: int) -> AsyncGenerator[int]:
+ while True:
+ yield start
+ start = await increment(start)
+
+ async def infinite_stream(start: int) -> AsyncGenerator[int, None]:
+ while True:
+ yield start
+ start = await increment(start)
+
+As in the synchronous case,
+:class:`AsyncIterable[YieldType] <collections.abc.AsyncIterable>`
+and :class:`AsyncIterator[YieldType] <collections.abc.AsyncIterator>` are
+available as well::
+
+ async def infinite_stream(start: int) -> AsyncIterator[int]:
+ while True:
+ yield start
+ start = await increment(start)
+
+Coroutines can be annotated using
+:class:`Coroutine[YieldType, SendType, ReturnType]
<collections.abc.Coroutine>`.
+Generic arguments correspond to those of :class:`~collections.abc.Generator`,
+for example::
+
+ from collections.abc import Coroutine
+ c: Coroutine[list[str], str, int] # Some coroutine defined elsewhere
+ x = c.send('hi') # Inferred type of 'x' is list[str]
+ async def bar() -> None:
+ y = await c # Inferred type of 'y' is int
+
.. _user-defined-generics:
User-defined generic types
@@ -3318,14 +3399,9 @@ Aliases to built-in types
Deprecated alias to :class:`dict`.
Note that to annotate arguments, it is preferred
- to use an abstract collection type such as :class:`Mapping`
+ to use an abstract collection type such as :class:`~collections.abc.Mapping`
rather than to use :class:`dict` or :class:`!typing.Dict`.
- This type can be used as follows::
-
- def count_words(text: str) -> Dict[str, int]:
- ...
-
.. deprecated:: 3.9
:class:`builtins.dict <dict>` now supports subscripting (``[]``).
See :pep:`585` and :ref:`types-genericalias`.
@@ -3335,16 +3411,9 @@ Aliases to built-in types
Deprecated alias to :class:`list`.
Note that to annotate arguments, it is preferred
- to use an abstract collection type such as :class:`Sequence` or
- :class:`Iterable` rather than to use :class:`list` or :class:`!typing.List`.
-
- This type may be used as follows::
-
- def vec2[T: (int, float)](x: T, y: T) -> List[T]:
- return [x, y]
-
- def keep_positives[T: (int, float)](vector: Sequence[T]) -> List[T]:
- return [item for item in vector if item > 0]
+ to use an abstract collection type such as
+ :class:`~collections.abc.Sequence` or :class:`~collections.abc.Iterable`
+ rather than to use :class:`list` or :class:`!typing.List`.
.. deprecated:: 3.9
:class:`builtins.list <list>` now supports subscripting (``[]``).
@@ -3355,8 +3424,8 @@ Aliases to built-in types
Deprecated alias to :class:`builtins.set <set>`.
Note that to annotate arguments, it is preferred
- to use an abstract collection type such as :class:`AbstractSet`
- rather than to use :class:`set` or :class:`!typing.Set`.
+ to use an abstract collection type such as :class:`collections.abc.Set`
+ rather than to use :class:`set` or :class:`typing.Set`.
.. deprecated:: 3.9
:class:`builtins.set <set>` now supports subscripting (``[]``).
@@ -3544,11 +3613,6 @@ Aliases to container ABCs in :mod:`collections.abc`
Deprecated alias to :class:`collections.abc.Mapping`.
- This type can be used as follows::
-
- def get_position_in_index(word_list: Mapping[str, int], word: str) ->
int:
- return word_list[word]
-
.. deprecated:: 3.9
:class:`collections.abc.Mapping` now supports subscripting (``[]``).
See :pep:`585` and :ref:`types-genericalias`.
@@ -3612,14 +3676,9 @@ Aliases to asynchronous ABCs in :mod:`collections.abc`
Deprecated alias to :class:`collections.abc.Coroutine`.
- The variance and order of type variables
- correspond to those of :class:`Generator`, for example::
-
- from collections.abc import Coroutine
- c: Coroutine[list[str], str, int] # Some coroutine defined elsewhere
- x = c.send('hi') # Inferred type of 'x' is list[str]
- async def bar() -> None:
- y = await c # Inferred type of 'y' is int
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`collections.abc.Coroutine`
+ and ``typing.Coroutine`` in type annotations.
.. versionadded:: 3.5.3
@@ -3631,40 +3690,9 @@ Aliases to asynchronous ABCs in :mod:`collections.abc`
Deprecated alias to :class:`collections.abc.AsyncGenerator`.
- An async generator can be annotated by the generic type
- ``AsyncGenerator[YieldType, SendType]``. For example::
-
- async def echo_round() -> AsyncGenerator[int, float]:
- sent = yield 0
- while sent >= 0.0:
- rounded = await round(sent)
- sent = yield rounded
-
- Unlike normal generators, async generators cannot return a value, so there
- is no ``ReturnType`` type parameter. As with :class:`Generator`, the
- ``SendType`` behaves contravariantly.
-
- The ``SendType`` defaults to :const:`!None`::
-
- async def infinite_stream(start: int) -> AsyncGenerator[int]:
- while True:
- yield start
- start = await increment(start)
-
- It is also possible to set this type explicitly::
-
- async def infinite_stream(start: int) -> AsyncGenerator[int, None]:
- while True:
- yield start
- start = await increment(start)
-
- Alternatively, annotate your generator as having a return type of
- either ``AsyncIterable[YieldType]`` or ``AsyncIterator[YieldType]``::
-
- async def infinite_stream(start: int) -> AsyncIterator[int]:
- while True:
- yield start
- start = await increment(start)
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`collections.abc.AsyncGenerator`
+ and ``typing.AsyncGenerator`` in type annotations.
.. versionadded:: 3.6.1
@@ -3746,40 +3774,9 @@ Aliases to other ABCs in :mod:`collections.abc`
Deprecated alias to :class:`collections.abc.Generator`.
- A generator can be annotated by the generic type
- ``Generator[YieldType, SendType, ReturnType]``. For example::
-
- def echo_round() -> Generator[int, float, str]:
- sent = yield 0
- while sent >= 0:
- sent = yield round(sent)
- return 'Done'
-
- Note that unlike many other generics in the typing module, the ``SendType``
- of :class:`Generator` behaves contravariantly, not covariantly or
- invariantly.
-
- The ``SendType`` and ``ReturnType`` parameters default to :const:`!None`::
-
- def infinite_stream(start: int) -> Generator[int]:
- while True:
- yield start
- start += 1
-
- It is also possible to set these types explicitly::
-
- def infinite_stream(start: int) -> Generator[int, None, None]:
- while True:
- yield start
- start += 1
-
- Alternatively, annotate your generator as having a return type of
- either ``Iterable[YieldType]`` or ``Iterator[YieldType]``::
-
- def infinite_stream(start: int) -> Iterator[int]:
- while True:
- yield start
- start += 1
+ See :ref:`annotating-generators-and-coroutines`
+ for details on using :class:`collections.abc.Generator`
+ and ``typing.Generator`` in type annotations.
.. deprecated:: 3.9
:class:`collections.abc.Generator` now supports subscripting (``[]``).
_______________________________________________
Python-checkins mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/python-checkins.python.org/
Member address: [email protected]