mirror of
https://github.com/python/cpython.git
synced 2026-01-06 15:32:22 +00:00
gh-74690: Document changes made to runtime-checkable protocols in 3.12 (#103348)
Co-authored-by: Jelle Zijlstra <jelle.zijlstra@gmail.com>
This commit is contained in:
parent
5d7d86f2fd
commit
644136563d
4 changed files with 64 additions and 9 deletions
|
|
@ -1598,15 +1598,6 @@ These are not used in annotations. They are building blocks for creating generic
|
|||
import threading
|
||||
assert isinstance(threading.Thread(name='Bob'), Named)
|
||||
|
||||
.. versionchanged:: 3.12
|
||||
The internal implementation of :func:`isinstance` checks against
|
||||
runtime-checkable protocols now uses :func:`inspect.getattr_static`
|
||||
to look up attributes (previously, :func:`hasattr` was used).
|
||||
As a result, some objects which used to be considered instances
|
||||
of a runtime-checkable protocol may no longer be considered instances
|
||||
of that protocol on Python 3.12+, and vice versa.
|
||||
Most users are unlikely to be affected by this change.
|
||||
|
||||
.. note::
|
||||
|
||||
:func:`!runtime_checkable` will check only the presence of the required
|
||||
|
|
@ -1628,6 +1619,24 @@ These are not used in annotations. They are building blocks for creating generic
|
|||
|
||||
.. versionadded:: 3.8
|
||||
|
||||
.. versionchanged:: 3.12
|
||||
The internal implementation of :func:`isinstance` checks against
|
||||
runtime-checkable protocols now uses :func:`inspect.getattr_static`
|
||||
to look up attributes (previously, :func:`hasattr` was used).
|
||||
As a result, some objects which used to be considered instances
|
||||
of a runtime-checkable protocol may no longer be considered instances
|
||||
of that protocol on Python 3.12+, and vice versa.
|
||||
Most users are unlikely to be affected by this change.
|
||||
|
||||
.. versionchanged:: 3.12
|
||||
The members of a runtime-checkable protocol are now considered "frozen"
|
||||
at runtime as soon as the class has been created. Monkey-patching
|
||||
attributes onto a runtime-checkable protocol will still work, but will
|
||||
have no impact on :func:`isinstance` checks comparing objects to the
|
||||
protocol. See :ref:`"What's new in Python 3.12" <whatsnew-typing-py312>`
|
||||
for more details.
|
||||
|
||||
|
||||
Other special directives
|
||||
""""""""""""""""""""""""
|
||||
|
||||
|
|
|
|||
|
|
@ -422,6 +422,8 @@ tempfile
|
|||
The :class:`tempfile.NamedTemporaryFile` function has a new optional parameter
|
||||
*delete_on_close* (Contributed by Evgeny Zorin in :gh:`58451`.)
|
||||
|
||||
.. _whatsnew-typing-py312:
|
||||
|
||||
typing
|
||||
------
|
||||
|
||||
|
|
@ -441,6 +443,39 @@ typing
|
|||
vice versa. Most users are unlikely to be affected by this change.
|
||||
(Contributed by Alex Waygood in :gh:`102433`.)
|
||||
|
||||
* The members of a runtime-checkable protocol are now considered "frozen" at
|
||||
runtime as soon as the class has been created. Monkey-patching attributes
|
||||
onto a runtime-checkable protocol will still work, but will have no impact on
|
||||
:func:`isinstance` checks comparing objects to the protocol. For example::
|
||||
|
||||
>>> from typing import Protocol, runtime_checkable
|
||||
>>> @runtime_checkable
|
||||
... class HasX(Protocol):
|
||||
... x = 1
|
||||
...
|
||||
>>> class Foo: ...
|
||||
...
|
||||
>>> f = Foo()
|
||||
>>> isinstance(f, HasX)
|
||||
False
|
||||
>>> f.x = 1
|
||||
>>> isinstance(f, HasX)
|
||||
True
|
||||
>>> HasX.y = 2
|
||||
>>> isinstance(f, HasX) # unchanged, even though HasX now also has a "y" attribute
|
||||
True
|
||||
|
||||
This change was made in order to speed up ``isinstance()`` checks against
|
||||
runtime-checkable protocols.
|
||||
|
||||
* The performance profile of :func:`isinstance` checks against
|
||||
:func:`runtime-checkable protocols <typing.runtime_checkable>` has changed
|
||||
significantly. Most ``isinstance()`` checks against protocols with only a few
|
||||
members should be at least 2x faster than in 3.11, and some may be 20x
|
||||
faster or more. However, ``isinstance()`` checks against protocols with seven
|
||||
or more members may be slower than in Python 3.11. (Contributed by Alex
|
||||
Waygood in :gh:`74690` and :gh:`103193`.)
|
||||
|
||||
sys
|
||||
---
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,3 @@
|
|||
The members of a runtime-checkable protocol are now considered "frozen" at
|
||||
runtime as soon as the class has been created. See
|
||||
:ref:`"What's new in Python 3.12" <whatsnew-typing-py312>` for more details.
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
The performance of :func:`isinstance` checks against
|
||||
:func:`runtime-checkable protocols <typing.runtime_checkable>` has been
|
||||
considerably improved for protocols that only have a few members. To achieve
|
||||
this improvement, several internal implementation details of the
|
||||
:mod:`typing` module have been refactored, including
|
||||
``typing._ProtocolMeta.__instancecheck__``,
|
||||
``typing._is_callable_members_only``, and ``typing._get_protocol_attrs``.
|
||||
Patches by Alex Waygood.
|
||||
Loading…
Add table
Add a link
Reference in a new issue