Что нового в Python 3.12

Редактор:

Адам Тернер

В этой статье рассказывается о новых возможностях Python 3.12 по сравнению с 3.11. Python 3.12 был выпущен 2 октября 2023 года. Более подробную информацию можно найти в changelog.

См.также

PEP 693 – График выхода Python 3.12

Резюме - Основные моменты выпуска

Python 3.12 - это последний стабильный выпуск языка программирования Python, содержащий множество изменений в языке и стандартной библиотеке. Изменения в библиотеке направлены на очистку устаревших API, удобство использования и корректность. Следует отметить, что пакет distutils был удален из стандартной библиотеки. Поддержка файловой системы в os и pathlib получила ряд улучшений, а некоторые модули стали более производительными.

Изменения в языке направлены на удобство использования, так как из f-strings было удалено множество ограничений, а предложения «Вы имели в виду…» продолжают улучшаться. Новые формулировки type parameter syntax и type улучшают эргономику использования generic types и type aliases со статическими программами проверки типов.

В этой статье не делается попытка дать полное описание всех новых возможностей, а вместо этого приводится удобный обзор. За подробной информацией следует обращаться к документации, такой как Library Reference и Language Reference. Если вы хотите получить полное представление о реализации и обосновании изменений, обратитесь к PEP для конкретной новой функции; но учтите, что PEP обычно не обновляются после полной реализации функции.


Новые возможности синтаксиса:

  • PEP 695, синтаксис параметров типа и оператор type

Новые возможности грамматики:

Улучшения в работе переводчика:

Улучшение модели данных Python:

Значительные улучшения в стандартной библиотеке:

  • Класс pathlib.Path теперь поддерживает подклассы

  • Модуль os получил несколько улучшений для поддержки Windows

  • Модуль command-line interface был добавлен к модулю sqlite3.

  • isinstance() проверяет против runtime-checkable protocols с ускорением от двух до 20 раз

  • Пакет asyncio получил ряд улучшений производительности: в некоторых бенчмарках скорость работы увеличилась на 75 %.

  • Модуль command-line interface был добавлен к модулю uuid.

  • Благодаря изменениям в PEP 701 производство токенов через модуль tokenize стало на 64 % быстрее.

Улучшения в системе безопасности:

  • Замените встроенные hashlib реализации SHA1, SHA3, SHA2-384, SHA2-512 и MD5 формально проверенным кодом из проекта HACL*. Эти встроенные реализации остаются в качестве запасных вариантов, которые используются только в тех случаях, когда OpenSSL их не предоставляет.

Улучшения в API на языке C:

  • PEP 697, нестабильный уровень API C

  • PEP 683, бессмертные предметы

Улучшения в реализации CPython:

  • PEP 709, инлайнинг понимания

  • CPython support для профилировщика Linux perf

  • Реализуйте защиту от переполнения стека на поддерживаемых платформах

Новые возможности набора текста:

Важные устаревания, удаления или ограничения:

  • PEP 623: Удалите wstr из объектов Unicode в C API Python, уменьшив размер каждого объекта str по крайней мере на 8 байт.

  • PEP 632: Удалите пакет distutils. Рекомендации по замене предоставляемых им API см. в разделе the migration guide. Сторонний пакет Setuptools продолжает предоставлять distutils, если он по-прежнему необходим в Python 3.12 и последующих версиях.

  • gh-95299: Не устанавливайте setuptools в виртуальных средах, созданных с помощью venv. Это означает, что distutils, setuptools, pkg_resources и easy_install больше не будут доступны по умолчанию; чтобы получить к ним доступ, запустите pip install setuptools в виртуальной среде activated.

  • Модули asynchat, asyncore и imp были удалены, а также несколько unittest.TestCase method aliases.

Новые возможности

PEP 695: Синтаксис параметра типа

Общие классы и функции под PEP 484 объявлялись с использованием многословного синтаксиса, который оставлял область видимости параметров типа неясной и требовал явного объявления дисперсии.

PEP 695 представляет новый, более компактный и явный способ создания generic classes и functions:

def max[T](args: Iterable[T]) -> T:
    ...

class list[T]:
    def __getitem__(self, index: int, /) -> T:
        ...

    def append(self, element: T) -> None:
        ...

Кроме того, PEP вводит новый способ объявления type aliases с помощью оператора type, который создает экземпляр TypeAliasType:

type Point = tuple[float, float]

Псевдонимы типов также могут быть generic:

type Point[T] = tuple[T, T]

Новый синтаксис позволяет объявлять TypeVarTuple и ParamSpec параметры, а также TypeVar параметры с границами или ограничениями:

type IntFunc[**P] = Callable[P, int]  # ParamSpec
type LabeledTuple[*Ts] = tuple[str, *Ts]  # TypeVarTuple
type HashableSequence[T: Hashable] = Sequence[T]  # TypeVar with bound
type IntOrStrSequence[T: (int, str)] = Sequence[T]  # TypeVar with constraints

Значение псевдонимов типов, а также границы и ограничения переменных типов, созданных с помощью этого синтаксиса, оцениваются только по требованию (см. lazy evaluation). Это означает, что псевдонимы типов могут ссылаться на другие типы, определенные позже в файле.

Параметры типа, объявленные через список параметров типа, видны в области видимости объявления и во всех вложенных областях, но не во внешней области видимости. Например, их можно использовать в аннотациях типов для методов общего класса или в теле класса. Однако их нельзя использовать в области видимости модуля после определения класса. Подробное описание семантики параметров типа во время выполнения см. в Списки параметров типа.

Для поддержки этой семантики вводится новый вид области видимости, annotation scope. Области аннотаций ведут себя по большей части как области функций, но по-разному взаимодействуют с окружающими областями классов. В Python 3.13 annotations также будет оцениваться в диапазонах аннотаций.

Более подробную информацию см. в разделе PEP 695.

(PEP написан Эриком Траутом. Реализация - Jelle Zijlstra, Eric Traut и другие в gh-103764).

PEP 701: Синтаксическая формализация f-строк

PEP 701 снимает некоторые ограничения на использование f-strings. Компоненты выражений внутри f-строк теперь могут быть любыми допустимыми выражениями Python, включая строки, использующие ту же кавычку, что и содержащая f-строка, многострочные выражения, комментарии, обратные слэши и юникодные управляющие последовательности. Давайте рассмотрим их подробнее:

  • Повторное использование кавычек: в Python 3.11 повторное использование тех же кавычек, что и во вложенной f-строке, вызывает ошибку SyntaxError, заставляя пользователя использовать другие доступные кавычки (например, двойные или тройные, если в f-строке используются одинарные кавычки). В Python 3.12 теперь можно делать примерно следующее:

    >>> songs = ['Take me back to Eden', 'Alkaline', 'Ascensionism']
    >>> f"This is the playlist: {", ".join(songs)}"
    'This is the playlist: Take me back to Eden, Alkaline, Ascensionism'
    

    Обратите внимание, что до этого изменения не было явного ограничения на вложенность f-строк, но тот факт, что строковые кавычки не могут быть повторно использованы внутри компонента выражения f-строки, делал невозможным произвольное вложение f-строк. Фактически, это самая вложенная f-строка, которую можно написать:

    >>> f"""{f'''{f'{f"{1+1}"}'}'''}"""
    '2'
    

    Поскольку теперь f-строки могут содержать любое допустимое выражение Python внутри компонентов выражения, появилась возможность произвольного вложения f-строк:

    >>> f"{f"{f"{f"{f"{f"{1+1}"}"}"}"}"}"
    '2'
    
  • Многострочные выражения и комментарии: В Python 3.11 выражения f-строк должны быть определены в одной строке, даже если выражение внутри f-строки может занимать несколько строк (например, литеральные списки могут быть определены в нескольких строках), что делает их более трудными для чтения. В Python 3.12 теперь можно определять f-строки в несколько строк и добавлять встроенные комментарии:

    >>> f"This is the playlist: {", ".join([
    ...     'Take me back to Eden',  # My, my, those eyes like fire
    ...     'Alkaline',              # Not acid nor alkaline
    ...     'Ascensionism'           # Take to the broken skies at last
    ... ])}"
    'This is the playlist: Take me back to Eden, Alkaline, Ascensionism'
    
  • Обратные косые черты и символы юникода: до Python 3.12 выражения f-строк не могли содержать символы \. Это также влияло на юникодные escape sequences (например, \N{snowman}), поскольку они содержат часть \N, которая ранее не могла входить в компоненты выражений f-строк. Теперь вы можете определять выражения следующим образом:

    >>> print(f"This is the playlist: {"\n".join(songs)}")
    This is the playlist: Take me back to Eden
    Alkaline
    Ascensionism
    >>> print(f"This is the playlist: {"\N{BLACK HEART SUIT}".join(songs)}")
    This is the playlist: Take me back to Eden♥Alkaline♥Ascensionism
    

Более подробную информацию см. в разделе PEP 701.

Положительным побочным эффектом реализации этой возможности (разбор f-строк с помощью the PEG parser) является то, что теперь сообщения об ошибках для f-строк более точны и включают точное местоположение ошибки. Например, в Python 3.11 следующая f-строка вызывает ошибку SyntaxError:

>>> my_string = f"{x z y}" + f"{1 + 1}"
  File "<stdin>", line 1
    (x z y)
     ^^^
SyntaxError: f-string: invalid syntax. Perhaps you forgot a comma?

но в сообщении об ошибке не указывается точное местоположение ошибки в строке, а также выражение искусственно окружено круглыми скобками. В Python 3.12, поскольку f-строки разбираются с помощью парсера PEG, сообщения об ошибках могут быть более точными и показывать всю строку:

>>> my_string = f"{x z y}" + f"{1 + 1}"
  File "<stdin>", line 1
    my_string = f"{x z y}" + f"{1 + 1}"
                   ^^^
SyntaxError: invalid syntax. Perhaps you forgot a comma?

(При участии Пабло Галиндо, Батухана Таская, Лисандроса Николау, Кристиана Маурейры-Фредеша и Марты Гомес в gh-102856. PEP написан Пабло Галиндо, Батуханом Таская, Лисандросом Николау и Мартой Гомес).

PEP 684: Пер-интерпретатор GIL

PEP 684 вводит возможность работы с каждым интерпретатором GIL, так что теперь можно создавать подинтерпретаторы с уникальным GIL для каждого интерпретатора. Это позволяет программам на Python использовать все преимущества нескольких ядер процессора. В настоящее время это доступно только через C-API, хотя API для Python уже anticipated for 3.13.

Используйте новую функцию Py_NewInterpreterFromConfig(), чтобы создать интерпретатор с собственным GIL:

PyInterpreterConfig config = {
    .check_multi_interp_extensions = 1,
    .gil = PyInterpreterConfig_OWN_GIL,
};
PyThreadState *tstate = NULL;
PyStatus status = Py_NewInterpreterFromConfig(&tstate, &config);
if (PyStatus_Exception(status)) {
    return -1;
}
/* The new interpreter is now active in the current thread. */

Другие примеры использования C-API для суб-интерпретаторов с GIL для каждого интерпретатора см. в Modules/_xxsubinterpretersmodule.c.

(Внесено Эриком Сноу в gh-104210 и т.д.)

PEP 669: Низкоударный мониторинг для CPython

PEP 669 определяет новый API для профилировщиков, отладчиков и других инструментов для мониторинга событий в CPython. Он охватывает широкий спектр событий, включая вызовы, возвраты, строки, исключения, переходы и многое другое. Это означает, что вы платите только за то, что используете, обеспечивая поддержку отладчиков и инструментов покрытия с почти нулевыми накладными расходами. Подробности см. в sys.monitoring.

(Внесено Марком Шенноном в gh-103082).

PEP 688: Создание доступа к буферному протоколу в Python

PEP 688 представляет способ использования buffer protocol из кода Python. Классы, реализующие метод __buffer__(), теперь можно использовать в качестве буферных типов.

Новый collections.abc.Buffer ABC обеспечивает стандартный способ представления буферных объектов, например, в аннотациях типов. Новое перечисление inspect.BufferFlags представляет флаги, которые могут быть использованы для настройки создания буфера. (Внесено Jelle Zijlstra в gh-102500).

PEP 709: Встраивание понимания

Постижения словарей, списков и множеств теперь встраиваются, а не создают новый объект одноразовой функции для каждого выполнения постижения. Это ускоряет выполнение постижения в два раза. Более подробную информацию см. в разделе PEP 709.

Итерационные переменные при осмыслении остаются изолированными и не перезаписывают одноименные переменные во внешней области видимости, а также не видны после осмысления. Инлайнинг приводит к нескольким заметным изменениям в поведении:

  • В трассировках больше нет отдельного фрейма для понимания, а трассировка/профилирование больше не показывает понимание как вызов функции.

  • Модуль symtable больше не будет создавать дочерние таблицы символов для каждого постижения; вместо этого локали постижения будут включаться в таблицу символов родительской функции.

  • Вызов locals() внутри понимания теперь включает переменные, находящиеся вне понимания, и больше не включает синтетическую переменную .0 для «аргумента» понимания.

  • При выполнении трассировки (например, при измерении покрытия кода) в процессе итерации над locals() (например, над [k for k in locals()]) может возникнуть ошибка «RuntimeError: dictionary changed size during iteration». Такое же поведение уже наблюдалось, например, в for k in locals():. Чтобы избежать ошибки, сначала создайте список ключей для итерации: keys = list(locals()); [k for k in keys].

(Предоставлено Карлом Мейером и Владимиром Матвеевым в PEP 709).

Улучшенные сообщения об ошибках

  • Модули из стандартной библиотеки теперь потенциально могут быть предложены в качестве части сообщений об ошибках, выводимых интерпретатором, когда NameError поднимается на верхний уровень. (Внесено Пабло Галиндо в gh-98254).

    >>> sys.version_info
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    NameError: name 'sys' is not defined. Did you forget to import 'sys'?
    
  • Улучшено предложение ошибок для исключений NameError для экземпляров. Теперь, если в методе поднимается NameError, а экземпляр имеет атрибут, точно совпадающий с именем в исключении, предложение будет включать self.<NAME> вместо ближайшего совпадения в области видимости метода. (Внесено Пабло Галиндо в gh-99139).

    >>> class A:
    ...    def __init__(self):
    ...        self.blech = 1
    ...
    ...    def foo(self):
    ...        somethin = blech
    ...
    >>> A().foo()
    Traceback (most recent call last):
      File "<stdin>", line 1
        somethin = blech
                   ^^^^^
    NameError: name 'blech' is not defined. Did you mean: 'self.blech'?
    
  • Улучшите сообщение об ошибке SyntaxError, когда пользователь набирает import x from y вместо from y import x. (Внесено Пабло Галиндо в gh-98931).

    >>> import a.y.z from b.y.z
    Traceback (most recent call last):
      File "<stdin>", line 1
        import a.y.z from b.y.z
        ^^^^^^^^^^^^^^^^^^^^^^^
    SyntaxError: Did you mean to use 'from ... import ...' instead?
    
  • Исключения ImportError, вызванные неудачными утверждениями from <module> import <name>, теперь включают предложения о значении <name>, основанные на доступных именах в <module>. (Внесено Пабло Галиндо в gh-91058).

    >>> from collections import chainmap
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    ImportError: cannot import name 'chainmap' from 'collections'. Did you mean: 'ChainMap'?
    

Другие языковые изменения

  • Парсер теперь поднимает SyntaxError при разборе исходного кода, содержащего нулевые байты. (Внесено Пабло Галиндо в gh-96670).

  • Пара обратный слеш-символ, не являющаяся допустимой управляющей последовательностью, теперь генерирует SyntaxWarning, а не DeprecationWarning. Например, re.compile("\d+\.\d+") теперь выдает SyntaxWarning ("\d" - недопустимая управляющая последовательность, используйте необработанные строки для регулярных выражений: re.compile(r"\d+\.\d+")). В одной из будущих версий Python вместо SyntaxWarning будет выдаваться SyntaxError. (Внесено Виктором Стиннером в gh-98401).

  • Октальные эскейпы со значением больше 0o377 (например, "\477"), устаревшие в Python 3.11, теперь выдают SyntaxWarning, а не DeprecationWarning. В одной из будущих версий Python они в конечном итоге будут иметь вид SyntaxError. (Внесено Виктором Стиннером в gh-98401).

  • Переменные, используемые в целевой части вычислений, которые не хранятся в памяти, теперь можно использовать в выражениях присваивания (:=). Например, в [(b := 1) for a, b.prop in some_iter] теперь разрешено присваивание b. Обратите внимание, что присваивание переменным, хранящимся в целевой части постижений (например, a), по-прежнему запрещено, как и в PEP 572. (Внесено Никитой Соболевым в gh-100581).

  • Исключения, возникающие в методе __set_name__ класса или типа, больше не оборачиваются символом RuntimeError. Информация о контексте добавляется к исключению в виде примечания PEP 678. (Внесено Ирит Катриэль в gh-77757).

  • Когда конструкция try-except* обрабатывает весь ExceptionGroup и вызывает еще одно исключение, это исключение больше не оборачивается в ExceptionGroup. Также изменено в версии 3.11.4. (Внесено Ирит Катриэль в gh-103590).

  • Теперь сборщик мусора работает только на механизме eval breaker цикла оценки байткода Python, а не на выделении объектов. GC также может запускаться при вызове PyErr_CheckSignals(), так что расширения на C, которым нужно долгое время работать без выполнения кода Python, также имеют возможность периодически запускать GC. (Внесено Пабло Галиндо в gh-97922).

  • Все встроенные и расширенные вызываемые модули, ожидающие булевых параметров, теперь принимают аргументы любого типа, а не только bool и int. (Внесено Сергеем Сторчакой в gh-60203).

  • memoryview теперь поддерживает тип half-float (код формата «e»). (Внесено Донгхи На и Антуаном Питру в gh-90751).

  • Объекты slice теперь хешируются, что позволяет использовать их в качестве ключей dict и элементов множеств. (Внесено Уиллом Брэдшоу, Фурканом Ондером и Раймондом Хеттингером в gh-101264).

  • sum() теперь использует суммирование Неймайера для повышения точности и коммутативности при суммировании плавающих чисел или смешанных интов и плавающих чисел. (Внесено Раймондом Хеттингером в gh-100425).

  • При разборе исходного кода, содержащего нулевой байт, ast.parse() теперь выдает SyntaxError, а не ValueError. (Внесено Пабло Галиндо в gh-96670).

  • Методы извлечения в tarfile и shutil.unpack_archive() имеют новый аргумент filter, который позволяет ограничить возможности tar, которые могут быть неожиданными или опасными, например создание файлов вне целевого каталога. Подробности см. в tarfile extraction filters. В Python 3.14 по умолчанию будет использоваться 'data'. (Внесено Петром Викториным в PEP 706).

  • Экземпляры types.MappingProxyType теперь хэшируются, если базовое отображение является хэшируемым. (Внесено Сергеем Сторчакой в gh-87995).

  • Добавьте support for the perf profiler с помощью новой переменной окружения PYTHONPERFSUPPORT и опции командной строки -X perf, а также новых функций sys.activate_stack_trampoline(), sys.deactivate_stack_trampoline() и sys.is_stack_trampoline_active(). (Дизайн Пабло Галиндо. Вклад Пабло Галиндо и Кристиана Хаймса при участии Грегори П. Смита [Google] и Марка Шеннона в gh-96123).

Новые модули

  • Нет.

Улучшенные модули

массив

  • Класс array.array теперь поддерживает подзапись, что делает его классом generic type. (Внесено Jelle Zijlstra в gh-98658).

asyncio

  • Производительность записи в сокеты в asyncio была значительно улучшена. asyncio теперь избегает ненужного копирования при записи в сокеты и использует sendmsg(), если платформа поддерживает его. (Внесено Кумаром Адитьей в gh-91166).

  • Добавьте функции asyncio.eager_task_factory() и asyncio.create_eager_task_factory(), позволяющие выбрать цикл событий для выполнения нетерпеливой задачи, что делает некоторые сценарии использования в 2-5 раз быстрее. (Внесено Джейкобом Боуэром и Итамаром Ореном в gh-102853, gh-104140 и gh-104138)

  • В Linux asyncio по умолчанию использует asyncio.PidfdChildWatcher, если os.pidfd_open() доступен и функционирует, вместо asyncio.ThreadedChildWatcher. (Внесено Кумаром Адитьей в gh-98024).

  • Цикл событий теперь использует наилучший доступный дочерний наблюдатель для каждой платформы (asyncio.PidfdChildWatcher, если поддерживается, и asyncio.ThreadedChildWatcher в противном случае), поэтому вручную настраивать дочерний наблюдатель не рекомендуется. (Внесено Кумаром Адитьей в gh-94597).

  • Добавьте параметр loop_factory в asyncio.run(), чтобы можно было указать собственную фабрику циклов событий. (Внесено Кумаром Адитьей в gh-99388).

  • Добавьте реализацию asyncio.current_task() на языке C для 4x-6x ускорения. (Внесено Итамаром Ореном и Пранавом Туласирамом Бхатом в gh-100344).

  • asyncio.iscoroutine() теперь возвращает False для генераторов, поскольку asyncio не поддерживает унаследованные корутины на основе генераторов. (Внесено Кумаром Адитьей в gh-102748).

  • asyncio.wait() и asyncio.as_completed() теперь принимают генераторы, дающие задания. (Внесено Кумаром Адитьей в gh-78530).

календарь

  • Добавьте перечисления calendar.Month и calendar.Day, определяющие месяцы года и дни недели. (Внесено принцем Рошаном в gh-103636).

csv

  • Добавьте флаги csv.QUOTE_NOTNULL и csv.QUOTE_STRINGS, чтобы обеспечить более тонкий контроль над None и пустыми строками с помощью объектов reader и writer.

dis

  • Опкоды псевдоинструкций (которые используются компилятором, но не отображаются в исполняемом байткоде) теперь отображаются в модуле dis. Модуль HAVE_ARGUMENT по-прежнему актуален для реальных опкодов, но для псевдоинструкций он бесполезен. Вместо него используйте новую коллекцию dis.hasarg. (Внесено Ирит Катриэль в gh-94216).

  • Добавьте коллекцию dis.hasexc для обозначения инструкций, устанавливающих обработчик исключений. (Внесено Ирит Катриэль в gh-94216).

фракции

  • Объекты типа fractions.Fraction теперь поддерживают форматирование в стиле float. (Внесено Марком Дикинсоном в gh-100161).

importlib.resources

осмотреть

  • Добавьте inspect.markcoroutinefunction(), чтобы отметить функции синхронизации, возвращающие coroutine, для использования с inspect.iscoroutinefunction(). (Внесено Карлтоном Гибсоном в gh-99247).

  • Добавьте inspect.getasyncgenstate() и inspect.getasyncgenlocals() для определения текущего состояния асинхронных генераторов. (Внесено Томасом Креннвалльнером в gh-79940).

  • Производительность inspect.getattr_static() была значительно улучшена. Большинство обращений к функции должно быть как минимум в 2 раза быстрее, чем в Python 3.11. (Внесено Алексом Уэйгудом в gh-103193).

itertools

  • Добавьте itertools.batched() для сбора в кортежи четного размера, когда последняя партия может быть короче остальных. (Внесено Раймондом Хеттингером в gh-98363).

математика

  • Добавьте math.sumprod() для вычисления суммы произведений. (Внесено Раймондом Хеттингером в gh-100485).

  • Расширьте math.nextafter(), добавив аргумент steps для перемещения вверх или вниз на несколько ступеней за раз. (Внесено Маттиасом Гергенсом, Марком Дикинсоном и Раймондом Хеттингером в gh-94906).

os

  • Добавьте os.PIDFD_NONBLOCK, чтобы открыть дескриптор файла для процесса с os.pidfd_open() в неблокирующем режиме. (Внесено Кумаром Адитьей в gh-93312).

  • os.DirEntry теперь включает метод os.DirEntry.is_junction() для проверки, является ли запись перекрестком. (Внесено Чарльзом Мачалоу в gh-99547).

  • Добавьте функции os.listdrives(), os.listvolumes() и os.listmounts() в Windows для перечисления дисков, томов и точек монтирования. (Внесено Стивом Дауэром в gh-102519).

  • Поля os.stat() и os.lstat() теперь более точны в Windows. Поле st_birthtime теперь будет заполняться временем создания файла, а st_ctime устарело, но по-прежнему содержит время создания (но в будущем будет возвращать последнее изменение метаданных, для согласованности с другими платформами). st_dev может быть до 64 бит, а st_ino - до 128 бит, в зависимости от вашей файловой системы, а st_rdev всегда устанавливается на ноль, а не на неверные значения. Обе функции могут быть значительно быстрее в новых версиях Windows. (Внесено Стивом Дауэром в gh-99726).

os.path

  • Добавьте os.path.isjunction(), чтобы проверить, является ли данный путь перекрестком. (Внесено Чарльзом Мачалоу в gh-99547).

  • Добавьте os.path.splitroot(), чтобы разбить путь на триаду (drive, root, tail). (Внесено Барни Гейлом в gh-101000).

pathlib

  • Добавьте поддержку подклассов pathlib.PurePath и pathlib.Path, а также их вариантов, специфичных для Posix и Windows. Подклассы могут переопределять метод pathlib.PurePath.with_segments() для передачи информации между экземплярами пути.

  • Добавьте pathlib.Path.walk() для обхода деревьев каталогов и генерации всех имен файлов или каталогов в них, аналогично os.walk(). (Внесено Станиславом Змиевым в gh-90385).

  • Добавьте необязательный параметр walk_up в pathlib.PurePath.relative_to(), чтобы разрешить вставку записей .. в результат; такое поведение более соответствует os.path.relpath(). (Внесено Доменико Рагузой в gh-84538).

  • Добавьте pathlib.Path.is_junction() в качестве прокси к os.path.isjunction(). (Внесено Чарльзом Мачалоу в gh-99547).

  • Добавьте необязательный параметр case_sensitive в pathlib.Path.glob(), pathlib.Path.rglob() и pathlib.PurePath.match() для соответствия чувствительности пути к регистру, что позволяет более точно контролировать процесс соответствия.

pdb

  • Добавьте удобные переменные, чтобы временно хранить значения для отладочной сессии и обеспечивать быстрый доступ к таким значениям, как текущий кадр или возвращаемое значение. (Внесено Тианом Гао в gh-103693).

случайно

ШУТИЛ

  • shutil.make_archive() теперь передает аргумент root_dir пользовательским архиваторам, которые его поддерживают. В этом случае он больше не будет временно менять текущий рабочий каталог процесса на root_dir для выполнения архивации. (Внесено Сергеем Сторчакой в gh-74696).

  • shutil.rmtree() теперь принимает новый аргумент onexc, который представляет собой обработчик ошибок, подобный onerror, но ожидающий экземпляр исключения, а не триплет (typ, val, tb). onerror устарел. (Внесено Ирит Катриэль в gh-102828).

  • shutil.which() теперь обращается к переменной окружения PATHEXT для поиска совпадений в пределах PATH в Windows, даже если заданный cmd включает компонент каталога. (Внесено Чарльзом Мачалоу в gh-103179).

    shutil.which() будет вызывать NeedCurrentDirectoryForExePathW при запросе исполняемых файлов в Windows, чтобы определить, нужно ли добавлять текущий рабочий каталог к пути поиска. (Внесено Чарльзом Мачалоу в gh-103179).

    shutil.which() вернет путь, соответствующий cmd с компонентом из PATHEXT до прямого совпадения в другом месте пути поиска в Windows. (Внесено Чарльзом Мачалоу в gh-103179).

sqlite3

статистика

  • Расширьте statistics.correlation(), включив в него в качестве ranked метод вычисления корреляции Спирмена для ранжированных данных. (Внесено Раймондом Хеттингером в gh-95861).

sys

  • Добавьте пространство имен sys.monitoring, чтобы открыть новый API мониторинга PEP 669. (Внесено Марком Шенноном в gh-103082).

  • Добавьте sys.activate_stack_trampoline() и sys.deactivate_stack_trampoline() для активации и деактивации батутов стекового профилировщика, а также sys.is_stack_trampoline_active() для запроса, активны ли батуты стекового профилировщика. (Внесено Пабло Галиндо и Кристианом Хаймсом при участии Грегори П. Смита [Google] и Марка Шеннона в gh-96123).

  • Добавьте sys.last_exc, в котором хранится последнее необработанное исключение, которое было поднято (для случаев посмертной отладки). Утратить три поля, содержащие ту же информацию в устаревшей форме: sys.last_type, sys.last_value и sys.last_traceback. (Внесено Ирит Катриэль в gh-102778).

  • sys._current_exceptions() теперь возвращает отображение из thread-id в экземпляр исключения, а не в кортеж (typ, exc, tb). (Внесено Ирит Катриэль в gh-103176).

  • sys.setrecursionlimit() и sys.getrecursionlimit(). Ограничение рекурсии теперь применяется только к коду Python. Встроенные функции не используют ограничение рекурсии, но защищены другим механизмом, который не позволяет рекурсии вызвать сбой виртуальной машины.

tempfile

  • В функции tempfile.NamedTemporaryFile появился новый необязательный параметр delete_on_close (Внесен Евгением Зориным в gh-58451).

  • tempfile.mkdtemp() теперь всегда возвращает абсолютный путь, даже если аргумент, указанный в параметре dir, является относительным путем.

нарезка резьбы

tkinter

  • tkinter.Canvas.coords() теперь сглаживает свои аргументы. Теперь он принимает не только координаты как отдельные аргументы (x1, y1, x2, y2, ...) и последовательность координат ([x1, y1, x2, y2, ...]), но и координаты, сгруппированные попарно ((x1, y1), (x2, y2), ... и [(x1, y1), (x2, y2), ...]), как методы create_*(). (Внесено Сергеем Сторчакой в gh-94473).

tokenize

  • Модуль tokenize включает в себя изменения, внесенные в PEP 701 (вклад Марты Гомес Масиас и Пабло Галиндо в gh-102856). См. Переход на Python 3.12 для получения дополнительной информации об изменениях в модуле tokenize.

типы

набор текста

  • При проверке isinstance() на runtime-checkable protocols теперь используется inspect.getattr_static(), а не hasattr() для поиска наличия атрибутов. Это означает, что дескрипторы и методы __getattr__() больше не будут неожиданно оцениваться при проверке isinstance() на соответствие протоколам, проверяемым во время выполнения. Однако это также может означать, что некоторые объекты, которые раньше считались экземплярами протокола, проверяемого временем выполнения, больше не будут считаться экземплярами этого протокола на Python 3.12+, и наоборот. Большинство пользователей вряд ли пострадают от этого изменения. (Внесено Алексом Уэйгудом в gh-102433).

  • Члены протокола, проверяемого временем выполнения, теперь считаются «замороженными» во время выполнения, как только класс был создан. Обезьяньи исправления атрибутов протокола, проверяемого временем выполнения, по-прежнему будут работать, но не будут влиять на проверки isinstance(), сравнивающие объекты с протоколом. Например:

    >>> 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
    

    Это изменение было сделано для того, чтобы ускорить проверку isinstance() на протоколах, проверяемых во время выполнения.

  • Профиль производительности проверок isinstance() против runtime-checkable protocols значительно изменился. Большинство isinstance() проверок протоколов с несколькими членами должны быть как минимум в 2 раза быстрее, чем в 3.11, а некоторые могут быть в 20 раз быстрее или больше. Однако проверки isinstance() протоколов с большим количеством членов могут быть медленнее, чем в Python 3.11. (Вклад Алекса Уэйгуда в gh-74690 и gh-103193).

  • Все классы typing.TypedDict и typing.NamedTuple теперь имеют атрибут __orig_bases__. (Внесено Адрианом Гарсией Бадаракко в gh-103699).

  • Добавьте параметр frozen_default в typing.dataclass_transform(). (Внесено Эриком де Бонте в gh-99957).

unicodedata

  • База данных Unicode была обновлена до версии 15.0.0. (Внесено Бенджамином Петерсоном в gh-96734).

unittest

Добавьте параметр командной строки --durations, показывающий N самых медленных тестовых случаев:

python3 -m unittest --durations=3 lib.tests.test_threading
.....
Slowest test durations
----------------------------------------------------------------------
1.210s     test_timeout (Lib.test.test_threading.BarrierTests)
1.003s     test_default_timeout (Lib.test.test_threading.BarrierTests)
0.518s     test_timeout (Lib.test.test_threading.EventTests)

(0.000 durations hidden.  Use -v to show these durations.)
----------------------------------------------------------------------
Ran 158 tests in 9.869s

OK (skipped=3)

(Внесено Джампаоло Родола в gh-48330)

uuid

Оптимизации

  • Удаляет члены wstr и wstr_length из объектов Unicode. Это уменьшает размер объекта на 8 или 16 байт на 64-разрядной платформе. (PEP 623) (Внесено Инадой Наоки в gh-92536).

  • Добавьте экспериментальную поддержку использования бинарного оптимизатора BOLT в процессе сборки, что повышает производительность на 1-5%. (Внесено Кевином Модзелевски в gh-90536 и настроено Донгхи На в gh-101525)

  • Ускорение подстановки регулярных выражений (функции re.sub() и re.subn() и соответствующие методы re.Pattern) для подстановки строк, содержащих групповые ссылки, в 2–3 раза. (Внесено Сергеем Сторчакой в gh-91524).

  • Ускорьте создание asyncio.Task, отложив дорогостоящее форматирование строк. (Внесено Итамаром Ореном в gh-103793).

  • Функции tokenize.tokenize() и tokenize.generate_tokens() работают на 64 % быстрее, что является побочным эффектом изменений, необходимых для покрытия PEP 701 в модуле tokenize. (Вклад Марты Гомес Масиас и Пабло Галиндо в gh-102856).

  • Ускорьте вызовы методов super() и загрузку атрибутов с помощью новой инструкции LOAD_SUPER_ATTR. (Вклад Карла Мейера и Владимира Матвеева в gh-103497).

Изменения байткода CPython

  • Удалите инструкцию LOAD_METHOD. Она была объединена с инструкцией LOAD_ATTR. Инструкция LOAD_ATTR теперь будет вести себя как старая инструкция LOAD_METHOD, если младший бит ее oparg установлен. (Внесено Кеном Джином в gh-93429).

  • Удалите инструкции JUMP_IF_FALSE_OR_POP и JUMP_IF_TRUE_OR_POP. (Внесено Ирит Катриэль в gh-102859).

  • Удалите инструкцию PRECALL. (Внесено Марком Шенноном в gh-92925).

  • Добавьте инструкции BINARY_SLICE и STORE_SLICE. (Внесено Марком Шенноном в gh-94163).

  • Добавьте инструкции CALL_INTRINSIC_1. (Внесено Марком Шенноном в gh-99005).

  • Добавьте инструкцию CALL_INTRINSIC_2. (Внесено Ирит Катриэль в gh-101799).

  • Добавьте инструкцию CLEANUP_THROW. (Внесено Брандтом Бухером в gh-90997).

  • Добавьте инструкцию END_SEND. (Внесено Марком Шенноном в gh-103082).

  • Добавьте инструкцию LOAD_FAST_AND_CLEAR как часть реализации PEP 709. (Внесено Карлом Мейером в gh-101441).

  • Добавьте инструкцию LOAD_FAST_CHECK. (Внесено Деннисом Суини в gh-93143).

  • Добавьте опкоды LOAD_FROM_DICT_OR_DEREF, LOAD_FROM_DICT_OR_GLOBALS и LOAD_LOCALS как часть реализации PEP 695. Удалите опкод LOAD_CLASSDEREF, который можно заменить на LOAD_LOCALS плюс LOAD_FROM_DICT_OR_DEREF. (Внесено Jelle Zijlstra в gh-103764).

  • Добавьте инструкцию LOAD_SUPER_ATTR. (Внесено Карлом Мейером и Владимиром Матвеевым в gh-103497).

  • Добавьте инструкцию RETURN_CONST. (Вклад Веньяна Ванга в gh-101632).

Демонстрации и инструменты

  • Удалите каталог Tools/demo/, содержащий старые демо-скрипты. Копию можно найти в old-demos project. (Внесено Виктором Стиннером в gh-97681).

  • Удалите устаревшие примеры скриптов из каталога Tools/scripts/. Копию можно найти в old-demos project. (Внесено Виктором Стиннером в gh-97669).

Утратившие актуальность

  • argparse: Параметры type, choices и metavar из argparse.BooleanOptionalAction устарели и будут удалены в 3.14. (Внесено Никитой Соболевым в gh-92248).

  • ast: Следующие функции ast были устаревшими в документации с Python 3.8, теперь вызывают DeprecationWarning во время выполнения при обращении к ним или их использовании, и будут удалены в Python 3.14:

    • ast.Num

    • ast.Str

    • ast.Bytes

    • ast.NameConstant

    • ast.Ellipsis

    Вместо этого используйте ast.Constant. (Внесено Сергеем Сторчакой в gh-90953).

  • asyncio:

  • calendar: Константы calendar.January и calendar.February устарели и заменены на calendar.JANUARY и calendar.FEBRUARY. (Внесено принцем Рошаном в gh-103636).

  • collections.abc: Утратившие актуальность collections.abc.ByteString. Предпочтите Sequence или collections.abc.Buffer. Для использования в типизации предпочтите объединение, например bytes | bytearray или collections.abc.Buffer. (Внесено Shantanu Jain в gh-91896).

  • datetime: datetime.datetime, utcnow() и utcfromtimestamp() устарели и будут удалены в будущей версии. Вместо этого используйте объекты, учитывающие временные зоны, для представления дат в UTC: соответственно, вызывайте now() и fromtimestamp() с параметром tz, установленным в datetime.UTC. (Внесено Полом Ганслом в gh-103857).

  • email: Утратить параметр isdst в email.utils.localtime(). (Внесено Аланом Уильямсом в gh-72346).

  • importlib.abc: Утратили актуальность следующие классы, которые планируется удалить в Python 3.14:

    • importlib.abc.ResourceReader

    • importlib.abc.Traversable

    • importlib.abc.TraversableResources

    Вместо этого используйте классы importlib.resources.abc:

    (Предоставлено Джейсоном Р. Кумбсом и Хьюго ван Кеменаде в gh-93963).

  • itertools: Откажитесь от поддержки операций copy, deepcopy и pickle, которые недокументированы, неэффективны, исторически ошибочны и непоследовательны. Они будут удалены в версии 3.14, что значительно сократит объем кода и нагрузку по сопровождению. (Внесено Раймондом Хеттингером в gh-101588).

  • multiprocessing: В Python 3.14 метод запуска multiprocessing по умолчанию будет заменен на более безопасный для Linux, BSD и других POSIX-платформ, отличных от macOS, где в настоящее время по умолчанию используется 'fork' (gh-84559). Добавление предупреждения об этом во время выполнения было сочтено слишком разрушительным, так как большинство кода, как ожидается, не будет беспокоиться об этом. Используйте get_context() или set_start_method() API, чтобы явно указать, когда ваш код требует 'fork'. См. contexts and start methods.

  • pkgutil: pkgutil.find_loader() и pkgutil.get_loader() устарели и будут удалены в Python 3.14; используйте вместо них importlib.util.find_spec(). (Внесено Никитой Соболевым в gh-97850).

  • pty: В модуле есть две недокументированные функции master_open() и slave_open(), которые были устаревшими со времен Python 2, но получили правильное обозначение DeprecationWarning только в 3.12. Удалите их в 3.14. (Внесено Soumendra Ganguly и Gregory P. Smith в gh-85984).

  • os:

    • Поля st_ctime, возвращаемые с помощью os.stat() и os.lstat() в Windows, устарели. В будущем выпуске они будут содержать время последнего изменения метаданных, что соответствует другим платформам. Пока же они по-прежнему содержат время создания, которое также доступно в новом поле st_birthtime. (Внесено Стивом Дауэром в gh-99726).

    • На POSIX-платформах os.fork() теперь может вызывать DeprecationWarning, если обнаруживает, что его вызывают из многопоточного процесса. При этом всегда существовала фундаментальная несовместимость с платформой POSIX. Даже если такой код кажется работающим. Мы добавили предупреждение, чтобы повысить осведомленность, поскольку проблемы, возникающие при выполнении такого кода, становятся все более частыми. См. документацию os.fork() для получения более подробной информации, а также this discussion on fork being incompatible with threads для объяснения того, почему мы теперь обращаем внимание разработчиков на эту давнюю проблему совместимости с платформой.

    Если это предупреждение появляется из-за использования multiprocessing или concurrent.futures, исправление заключается в использовании другого метода запуска multiprocessing, например "spawn" или "forkserver".

  • shutil: Аргумент onerror из shutil.rmtree() устарел; вместо него используйте onexc. (Внесено Ирит Катриэль в gh-102828).

  • sqlite3:

  • sys: Поля sys.last_type, sys.last_value и sys.last_traceback устарели. Вместо них используйте sys.last_exc. (Внесено Ирит Катриэль в gh-102778).

  • tarfile: Извлечение tar-архивов без указания фильтра устарело до Python 3.14, когда фильтр 'data' станет фильтром по умолчанию. Подробнее см. в разделе Фильтры для извлечения.

  • typing:

    • typing.Hashable теперь устарели. Вместо этого используйте typing.Sized и адаптируйте их под свои нужды. […] […]

    • typing.ByteString теперь устарели. Вместо этого используйте DeprecationWarning и адаптируйте их под свои нужды. […] […]

  • xml.etree.ElementTree: Теперь модуль выдает DeprecationWarning при проверке истинности значения xml.etree.ElementTree.Element. До этого реализация на Python выдавала FutureWarning, а реализация на C не выдавала ничего. (Внесено Джейкобом Уоллсом в gh-83122).

  • Трехарговые сигнатуры (type, value, traceback) функций coroutine throw(), generator throw() и async generator throw() устарели и могут быть удалены в будущих версиях Python. Вместо них используйте одноарговые версии этих функций. (Внесено Офей Чаном в gh-89874).

  • DeprecationWarning теперь поднимается, если __package__ на модуле отличается от __spec__.parent (ранее это было ImportWarning). (Внесено Бреттом Кэнноном в gh-65961).

  • Установка __package__ или __cached__ для модуля устарела и перестанет устанавливаться или учитываться системой импорта в Python 3.14. (Внесено Бреттом Кэнноном в gh-65961).

  • Оператор побитовой инверсии (~) для bool устарел. В Python 3.14 он будет вызывать ошибку. Вместо него используйте not для логического отрицания bool. В редких случаях, когда вам действительно нужна побитовая инверсия базового int, преобразуйте его в int явно: ~int(x). (Внесено Тимом Хоффманом в gh-103487).

  • Доступ к co_lnotab для объектов кода был устаревшим в Python 3.10 через PEP 626, но только в 3.12 он получил правильное DeprecationWarning, поэтому будет удален в 3.14. (Внесено Никитой Соболевым в gh-101866).

Отложенное удаление в Python 3.13

Следующие модули и API были устаревшими в предыдущих выпусках Python и будут удалены в Python 3.13.

Модули (см. PEP 594):

  • aifc

  • audioop

  • cgi

  • cgitb

  • chunk

  • crypt

  • imghdr

  • mailcap

  • msilib

  • nis

  • nntplib

  • ossaudiodev

  • pipes

  • sndhdr

  • spwd

  • sunau

  • telnetlib

  • uu

  • xdrlib

Другие модули:

  • lib2to3, а программа 2to3 (gh-84540)

API:

Удаление ожиданий в Python 3.14

Следующие API были устаревшими и будут удалены в Python 3.14.

  • argparse: Параметры type, choices и metavar из argparse.BooleanOptionalAction.

  • ast:

    • ast.Num

    • ast.Str

    • ast.Bytes

    • ast.NameConstant

    • ast.Ellipsis

  • asyncio:

    • asyncio.MultiLoopChildWatcher

    • asyncio.FastChildWatcher

    • asyncio.AbstractChildWatcher

    • asyncio.SafeChildWatcher

    • asyncio.set_child_watcher()

    • asyncio.get_child_watcher(),

    • asyncio.AbstractEventLoopPolicy.set_child_watcher()

    • asyncio.AbstractEventLoopPolicy.get_child_watcher()

  • collections.abc: collections.abc.ByteString.

  • email: параметр isdst в email.utils.localtime().

  • importlib.abc:

    • importlib.abc.ResourceReader

    • importlib.abc.Traversable

    • importlib.abc.TraversableResources

  • itertools: Поддержка операций копирования, глубокого копирования и pickle.

  • pkgutil:

    • pkgutil.find_loader()

    • pkgutil.get_loader().

  • pty:

    • pty.master_open()

    • pty.slave_open()

  • shutil: Аргумент onerror из shutil.rmtree().

  • typing: typing.ByteString

  • xml.etree.ElementTree: Проверка истинности значения xml.etree.ElementTree.Element.

  • Атрибуты __package__ и __cached__ на объектах модуля.

  • Атрибут co_lnotab объектов кода.

Удаление ожиданий в Python 3.15

Следующие API были устаревшими и будут удалены в Python 3.15.

API:

Ожидается удаление в будущих версиях

Следующие API были устаревшими в предыдущих версиях Python и будут удалены, хотя на данный момент дата их удаления не назначена.

  • Код формата array для 'u' (gh-57281)

  • typing.Text (gh-92332)

  • В настоящее время Python принимает числовые литералы, за которыми сразу следуют ключевые слова, например 0in x, 1or x, 0if 1else 2. Это позволяет использовать такие запутанные и неоднозначные выражения, как [0x1for x in y] (которое может быть интерпретировано как [0x1 for x in y] или [0x1f or x in y]). Если за числовым литералом сразу следует одно из ключевых слов and, else, for, if, in, is и or, то выдается синтаксическое предупреждение. В будущем выпуске это будет заменено на синтаксическую ошибку. (gh-87999)

Удалено

asynchat и asyncore

  • Эти два модуля были удалены в соответствии с расписанием в PEP 594, поскольку были устаревшими в Python 3.6. Вместо них используйте asyncio. (Внесено Никитой Соболевым в gh-96580).

configparser

  • Несколько имен, устаревших в configparser еще в 3.2, были удалены в gh-89336:

    • У configparser.ParsingError больше нет атрибута или аргумента filename. Вместо этого используйте атрибут и аргумент source.

    • У configparser больше нет класса SafeConfigParser. Вместо него используйте более короткое имя ConfigParser.

    • У configparser.ConfigParser больше нет метода readfp. Вместо него используйте read_file().

distutils

  • Удалите пакет distutils. Он был устаревшим в Python 3.10 благодаря PEP 632 «Deprecate distutils module». Для проектов, которые все еще используют distutils и не могут быть обновлены на что-то другое, можно установить проект setuptools: он по-прежнему предоставляет distutils. (Внесено Виктором Стиннером в gh-92584).

ensurepip

  • Удалите поставляемое колесо setuptools из ensurepip и прекратите установку setuptools в окружениях, созданных venv.

    pip (>= 22.1) не требует установки setuptools в окружении. Пакеты на основе setuptoolsdistutils) все еще можно использовать с pip install, поскольку pip обеспечит setuptools в среде сборки, которую он использует для сборки пакета.

    easy_install, pkg_resources, setuptools и distutils больше не предоставляются по умолчанию в окружениях, созданных с помощью venv или загруженных с помощью ensurepip, поскольку они являются частью пакета setuptools. Для проектов, полагающихся на них во время выполнения, проект setuptools должен быть объявлен как зависимость и установлен отдельно (обычно с помощью pip).

    (Предоставлено Pradyun Gedam в gh-95299).

enum

  • Удалите enum из EnumMeta.__getattr__, который больше не нужен для доступа к атрибутам перечисления. (Внесено Итаном Фурманом в gh-95083).

ftplib

  • Удалите атрибут класса ftplib из FTP_TLS.ssl_version: вместо него используйте параметр context. (Внесено Виктором Стиннером в gh-94172).

gzip

  • Удалите атрибут filename из gzip в gzip.GzipFile, устаревший с Python 2.6, вместо него используйте атрибут name. В режиме записи атрибут filename добавлял расширение файла '.gz', если оно отсутствовало. (Внесено Виктором Стиннером в gh-94196).

hashlib

  • Удалите чисто питоновскую реализацию hashlib для hashlib.pbkdf2_hmac(), устаревшую в Python 3.10. Для Python 3.10 и новее требуется OpenSSL 1.1.1 (PEP 644): эта версия OpenSSL обеспечивает реализацию pbkdf2_hmac() на C, которая работает быстрее. (Внесено Виктором Стиннером в gh-94199).

importlib

  • Многие ранее устаревшие очистки в importlib теперь завершены:

    • Ссылки на module_repr() и поддержка module_repr() были удалены. (Внесено Барри Варшавом в gh-97850).

    • importlib.util.set_package, importlib.util.set_loader и importlib.util.module_for_loader были удалены. (Вклад Бретта Кэннона и Никиты Соболева в gh-65961 и gh-97850).

    • Поддержка find_loader() и find_module() API была удалена. (Внесено Барри Варшавой в gh-98040).

    • importlib.abc.Finder, pkgutil.ImpImporter и pkgutil.ImpLoader были удалены. (Внесено Барри Варшавой в gh-98040).

имп

  • Модуль imp был удален. (Внесен Барри Варшавой в gh-98040).

    Для миграции обратитесь к следующей таблице соответствия:

    имп

    importlib

    imp.NullImporter

    Вставьте None в sys.path_importer_cache

    imp.cache_from_source()

    importlib.util.cache_from_source()

    imp.find_module()

    importlib.util.find_spec()

    imp.get_magic()

    importlib.util.MAGIC_NUMBER

    imp.get_suffixes()

    importlib.machinery.SOURCE_SUFFIXES, importlib.machinery.EXTENSION_SUFFIXES и importlib.machinery.BYTECODE_SUFFIXES.

    imp.get_tag()

    sys.implementation.cache_tag

    imp.load_module()

    importlib.import_module()

    imp.new_module(name)

    types.ModuleType(name)

    imp.reload()

    importlib.reload()

    imp.source_from_cache()

    importlib.util.source_from_cache()

    imp.load_source()

    Смотрите ниже

    Замените imp.load_source() на:

    import importlib.util
    import importlib.machinery
    
    def load_source(modname, filename):
        loader = importlib.machinery.SourceFileLoader(modname, filename)
        spec = importlib.util.spec_from_file_location(modname, filename, loader=loader)
        module = importlib.util.module_from_spec(spec)
        # The module is always executed and not cached in sys.modules.
        # Uncomment the following line to cache the module.
        # sys.modules[module.__name__] = module
        loader.exec_module(module)
        return module
    
  • Удалите функции и атрибуты imp, не имеющие замены:

    • Недокументированные функции:

      • imp.init_builtin()

      • imp.load_compiled()

      • imp.load_dynamic()

      • imp.load_package()

    • imp.lock_held(), imp.acquire_lock(), imp.release_lock(): в Python 3.3 схема блокировки изменилась и теперь блокировка осуществляется по модулям.

    • imp.find_module() константы: SEARCH_ERROR, PY_SOURCE, PY_COMPILED, C_EXTENSION, PY_RESOURCE, PKG_DIRECTORY, C_BUILTIN, PY_FROZEN, PY_CODERESOURCE, IMP_HOOK.

io

  • Удалите из io функции io.OpenWrapper и _pyio.OpenWrapper, устаревшие в Python 3.10: вместо них используйте open(). Функция open() (io.open()) является встроенной функцией. Начиная с Python 3.10, _pyio.open() также является статическим методом. (Внесено Виктором Стиннером в gh-94169).

локаль

  • Удалите функцию locale из locale.format(), устаревшую в Python 3.7: вместо нее используйте locale.format_string(). (Внесено Виктором Стиннером в gh-94226).

smtpd

  • Модуль smtpd был удален в соответствии с графиком, приведенным в PEP 594, и был устаревшим в Python 3.4.7 и 3.5.4. Используйте aiosmtpd модуль PyPI или любой другой asyncio-сервер вместо него. (Внесено Олегом Иарыгиным в gh-93243).

sqlite3

  • Следующие недокументированные функции sqlite3, устаревшие в Python 3.10, теперь удалены:

    • sqlite3.enable_shared_cache()

    • sqlite3.OptimizedUnicode

    Если необходимо использовать общий кэш, откройте базу данных в режиме URI с помощью параметра запроса cache=shared.

    Текстовая фабрика sqlite3.OptimizedUnicode стала псевдонимом для str начиная с Python 3.3. Код, который ранее устанавливал для фабрики текста значение OptimizedUnicode, может либо использовать str явно, либо полагаться на значение по умолчанию, которое также является str.

    (Предоставлено Эрлендом Э. Аасланом в gh-92548).

ssl

  • Удалите функцию ssl из ssl.RAND_pseudo_bytes(), устаревшую в Python 3.6: вместо нее используйте os.urandom() или ssl.RAND_bytes(). (Внесено Виктором Стиннером в gh-94199).

  • Удалите функцию ssl.match_hostname(). Она была устаревшей в Python 3.7. OpenSSL выполняет сопоставление имен хостов начиная с Python 3.7, Python больше не использует функцию ssl.match_hostname(). (Внесено Виктором Стиннером в gh-94199).

  • Уберите функцию ssl.wrap_socket(), устаревшую в Python 3.7: вместо нее создайте объект ssl.SSLContext и вызовите его метод ssl.SSLContext.wrap_socket. Любой пакет, который все еще использует ssl.wrap_socket(), сломан и небезопасен. Функция не отправляет расширение SNI TLS и не проверяет имя хоста сервера. Код подвержен CWE-295 (Неправильная проверка сертификата). (Внесено Виктором Стиннером в gh-94199).

unittest

веб-браузер

  • Удалите поддержку устаревших браузеров из webbrowser. К удаленным браузерам относятся: Grail, Mosaic, Netscape, Galeon, Skipstone, Iceape, Firebird и Firefox версий 35 и ниже (gh-102871).

xml.etree.ElementTree

  • Удалите метод ElementTree.Element.copy() из чисто питоновской реализации, устаревший в Python 3.10, вместо него используйте функцию copy.copy(). Реализация xml.etree.ElementTree на языке C не имеет метода copy(), только метод __copy__(). (Внесено Виктором Стиннером в gh-94383).

zipimport

  • Удалите методы zipimport find_loader() и find_module(), устаревшие в Python 3.10: вместо них используйте метод find_spec(). Обоснование смотрите в PEP 451. (Внесено Виктором Стиннером в gh-94379).

Другие

  • Удалите правило suspicious из документации Makefile и Doc/tools/rstlint.py в пользу sphinx-lint. (Внесено Жюльеном Паларом в gh-98179).

  • Удалите параметры keyfile и certfile из модулей ftplib, imaplib, poplib и smtplib, а также параметры key_file, cert_file и check_hostname из модуля http.client. Все они устарели с версии Python 3.6. Вместо них используйте параметр context (ssl_context в imaplib). (Внесено Виктором Стиннером в gh-94172).

  • Удалите хаки совместимости с Jython из нескольких модулей и тестов stdlib. (Внесено Никитой Соболевым в gh-99482).

  • Уберите флаг _use_broken_old_ctypes_structure_semantics_ из модуля ctypes. (Внесено Никитой Соболевым в gh-99285).

Переход на Python 3.12

В этом разделе перечислены ранее описанные изменения и другие исправления, которые могут потребовать внесения изменений в ваш код.

Изменения в API Python

  • Для числовых ссылок на группы и имен групп в регулярных выражениях теперь применяются более строгие правила. Теперь в качестве числовой ссылки принимается только последовательность ASCII-цифр. Имя группы в байтовых шаблонах и строках замены теперь может содержать только буквы и цифры ASCII и знак подчеркивания. (Внесено Сергеем Сторчакой в gh-91760).

  • Удалите функциональность randrange(), устаревшую с Python 3.10. Раньше randrange(10.0) без потерь преобразовывался в randrange(10). Теперь при этом возникает ошибка TypeError. Кроме того, исключение, возникающее для нецелых значений, таких как randrange(10.5) или randrange('10'), было изменено с ValueError на TypeError. Это также предотвращает ошибки, когда randrange(1e25) молча выбирает из большего диапазона, чем randrange(10**25). (Первоначально предложено Сергеем Сторчакой gh-86388).

  • argparse.ArgumentParser изменил кодировку и обработчик ошибок при чтении аргументов из файла (например, опция fromfile_prefix_chars) со стандартной текстовой кодировки (например, locale.getpreferredencoding(False)) на filesystem encoding and error handler. Файлы аргументов должны быть закодированы в UTF-8 вместо ANSI Codepage в Windows.

  • Удалите модуль asyncore-базированный smtpd, устаревший в Python 3.4.7 и 3.5.4. Рекомендуемая замена - asyncio-базированный aiosmtpd. модуль PyPI.

  • Удалите модуль shlex.split()-базированный None, устаревший в Python 3.4.7 и 3.5.4. Рекомендуемая замена - sys.stdin-базированный gh-94352. модуль PyPI. […]

  • Удалите модуль os-базированный bytearray, устаревший в Python 3.4.7 и 3.5.4. Рекомендуемая замена - memoryview-базированный bytes. модуль PyPI. […]

  • Удалите модуль syslog.openlog()-базированный syslog.closelog(), устаревший в Python 3.4.7 и 3.5.4. Рекомендуемая замена - syslog.syslog()-базированный syslog.openlog(). модуль PyPI. […]

  • Недокументированное поведение блокировки cached_property() удалено, поскольку она блокировала все экземпляры класса, что приводило к высокой конкуренции блокировок. Это означает, что функция получения кэшированного свойства теперь может выполняться более одного раза для одного экземпляра, если два потока работают в гонке. Для большинства простых кэшируемых свойств (например, тех, которые являются идемпотентными и просто вычисляют значение на основе других атрибутов экземпляра) это будет нормально. Если необходима синхронизация, реализуйте блокировку внутри функции получения кэшированного свойства или вокруг многопоточных точек доступа.

  • sys._current_exceptions() теперь возвращает отображение из thread-id в экземпляр исключения, а не в кортеж (typ, exc, tb). (Внесено Ирит Катриэль в gh-103176).

  • При извлечении tar-файлов с помощью tarfile или shutil.unpack_archive() передайте аргумент filter, чтобы ограничить возможности, которые могут быть неожиданными или опасными. Подробности см. в разделе Фильтры для извлечения.

  • Вывод функций tokenize.tokenize() и tokenize.generate_tokens() теперь изменен в связи с изменениями, внесенными в PEP 701. Это означает, что токены STRING больше не выдаются для f-строк, а вместо них теперь выдаются токены, описанные в PEP 701: FSTRING_START, FSTRING_MIDDLE и FSTRING_END теперь выдаются для частей f-строки «string» в дополнение к соответствующим токенам для токенизации в компонентах выражения. Например, для f-строки f"start {1+1} end" старая версия токенизатора выдавала:

    1,0-1,18:           STRING         'f"start {1+1} end"'
    

    в то время как новая версия выдает:

    1,0-1,2:            FSTRING_START  'f"'
    1,2-1,8:            FSTRING_MIDDLE 'start '
    1,8-1,9:            OP             '{'
    1,9-1,10:           NUMBER         '1'
    1,10-1,11:          OP             '+'
    1,11-1,12:          NUMBER         '1'
    1,12-1,13:          OP             '}'
    1,13-1,17:          FSTRING_MIDDLE ' end'
    1,17-1,18:          FSTRING_END    '"'
    

    Недокументированное поведение блокировки PEP 701 удалено, поскольку она блокировала все экземпляры класса, что приводило к высокой конкуренции блокировок. Это означает, что функция получения кэшированного свойства теперь может выполняться более одного раза для одного экземпляра, если два потока работают в гонке. […] […]

    • Недокументированное поведение блокировки type удалено, поскольку она блокировала все экземпляры класса, что приводило к высокой конкуренции блокировок. Это означает, что функция получения кэшированного свойства теперь может выполняться более одного раза для одного экземпляра, если два потока работают в гонке. […] […]

    • Недокументированное поведение блокировки tokenize.TokenError удалено, поскольку она блокировала все экземпляры класса, что приводило к высокой конкуренции блокировок. Это означает, что функция получения кэшированного свойства теперь может выполняться более одного раза для одного экземпляра, если два потока работают в гонке. […] […]

    • Недокументированное поведение блокировки tokenize.TokenError удалено, поскольку она блокировала все экземпляры класса, что приводило к высокой конкуренции блокировок. Это означает, что функция получения кэшированного свойства теперь может выполняться более одного раза для одного экземпляра, если два потока работают в гонке. […] […]

    • Смешивание табуляции и пробелов в качестве отступа в одном файле больше не поддерживается и приведет к ошибке TabError.

  • Модуль threading теперь ожидает, что модуль _thread будет иметь атрибут _is_main_interpreter. Это функция без аргументов, которая возвращает True, если текущий интерпретатор является основным.

    Любая библиотека или приложение, предоставляющее пользовательский модуль _thread, должно предоставлять _is_main_interpreter() (см. gh-112826).

Изменения в конструкции

  • Python больше не использует setup.py для сборки общих модулей расширения C. Параметры сборки, такие как заголовки и библиотеки, определяются в скрипте configure. Расширения собираются с помощью Makefile. Большинство расширений используют pkg-config и возвращаются к ручному обнаружению. (Внесено Кристианом Хаймсом в gh-93939).

  • va_start() с двумя параметрами, как va_start(args, format),, теперь требуется для сборки Python. va_start() больше не вызывается с одним параметром. (Внесено Кумаром Адитьей в gh-93207).

  • CPython теперь использует опцию ThinLTO в качестве политики оптимизации времени соединения по умолчанию, если компилятор Clang принимает этот флаг. (Внесено Donghee Na в gh-89536).

  • Добавьте переменную COMPILEALL_OPTS в Makefile, чтобы переопределить опции compileall (по умолчанию: -j0) в make install. Также объединены 3 команды compileall в одну команду для создания .pyc-файлов для всех уровней оптимизации (0, 1, 2) одновременно. (Внесено Виктором Стиннером в gh-99289).

  • Добавьте платформенные триплеты для 64-битного LoongArch:

    • loongarch64-linux-gnusf

    • loongarch64-linux-gnuf32

    • loongarch64-linux-gnu

    (Внесено Чжан На в gh-90656).

  • PYTHON_FOR_REGEN теперь требует Python 3.10 или более новой версии.

  • Для регенерации !configure теперь требуется Autoconf 2.71 и aclocal 1.16.4. (Внесено Кристианом Хаймсом в gh-89886).

  • Сборки для Windows и установщики для macOS с сайта python.org теперь используют OpenSSL 3.0.

Изменения в API на языке C

Новые возможности

  • PEP 697: Представляем Unstable C API tier, предназначенный для низкоуровневых инструментов, таких как отладчики и JIT-компиляторы. Этот API может изменяться в каждом младшем выпуске CPython без предупреждений об устаревании. Его содержимое обозначается префиксом PyUnstable_ в именах.

    Конструкторы кодовых объектов:

    • PyUnstable_Code_New() (переименовано из PyCode_New)

    • PyUnstable_Code_NewWithPosOnlyArgs() (переименовано из PyCode_NewWithPosOnlyArgs)

    Дополнительное хранилище для объектов кода (PEP 523):

    • PyUnstable_Eval_RequestCodeExtraIndex() (переименовано из _PyEval_RequestCodeExtraIndex)

    • PyUnstable_Code_GetExtra() (переименовано из _PyCode_GetExtra)

    • PyUnstable_Code_SetExtra() (переименовано из _PyCode_SetExtra)

    Оригинальные названия будут доступны до тех пор, пока не изменится соответствующий API.

    (Внесено Петром Викториным в gh-101101).

  • PEP 697: Добавьте API для расширения типов, чья компоновка памяти экземпляров непрозрачна:

    • PyType_Spec.basicsize может быть нулевым или отрицательным, чтобы указать на наследование или расширение размера базового класса.

    • PyObject_GetTypeData() и PyType_GetTypeDataSize() добавлены для доступа к данным экземпляра, специфичным для подкласса.

    • Py_TPFLAGS_ITEMS_AT_END и PyObject_GetItemData() добавлены для безопасного расширения некоторых типов с переменным размером, включая PyType_Type.

    • Py_RELATIVE_OFFSET добавлено, чтобы позволить определять members в терминах структуры, специфичной для подкласса.

    (Внесено Петром Викториным в gh-103509).

  • Добавьте новую функцию limited C API PyType_FromMetaclass(), которая обобщает существующую PyType_FromModuleAndSpec(), используя дополнительный аргумент метакласса. (Внесено Венцелем Якобом в gh-93012).

  • В Limited API добавлен API для создания объектов, которые можно вызывать с помощью the vectorcall protocol:

    Флаг Py_TPFLAGS_HAVE_VECTORCALL теперь снимается с класса при переназначении его метода __call__(). Это делает vectorcall безопасным для использования с мутабельными типами (т. е. типами кучи без флага неизменяемости, Py_TPFLAGS_IMMUTABLETYPE). Мутабельные типы, не переопределяющие tp_call, теперь наследуют флаг Py_TPFLAGS_HAVE_VECTORCALL. (Внесено Петром Викторином в gh-93274).

    Добавлены флаги Py_TPFLAGS_MANAGED_DICT и Py_TPFLAGS_MANAGED_WEAKREF. Это позволяет классам расширений поддерживать объектные __dict__ и слабые ссылки с меньшим количеством записей, используя меньше памяти и имея более быстрый доступ.

  • В Limited API добавлен API для выполнения вызовов с помощью the vectorcall protocol:

    Это означает, что в Limited API теперь доступны и входящий, и исходящий концы протокола векторного вызова. (Внесено Венцелем Якобом в gh-98586).

  • Добавьте две новые публичные функции, PyEval_SetProfileAllThreads() и PyEval_SetTraceAllThreads(), которые позволяют установить функции трассировки и профилирования во всех запущенных потоках, помимо вызывающего. (Внесено Пабло Галиндо в gh-93503).

  • Добавьте в C API новую функцию PyFunction_SetVectorcall(), которая устанавливает поле векторного вызова для данного PyFunctionObject. (Внесено Эндрю Фростом в gh-92257).

  • API языка C теперь позволяет регистрировать обратные вызовы через PyDict_AddWatcher(), PyDict_Watch() и связанные с ними API, которые будут вызываться при каждом изменении словаря. Это предназначено для использования оптимизирующими интерпретаторами, JIT-компиляторами или отладчиками. (Внесено Карлом Мейером в gh-91052).

  • Добавьте PyType_AddWatcher() и PyType_Watch() API для регистрации обратных вызовов, чтобы получать уведомления об изменении типа. (Внесено Карлом Мейером в gh-91051).

  • Добавьте PyCode_AddWatcher() и PyCode_ClearWatcher() API для регистрации обратных вызовов для получения уведомлений о создании и уничтожении объектов кода. (Внесено Итамаром Ореном в gh-91054).

  • Добавьте функции PyFrame_GetVar() и PyFrame_GetVarString(), чтобы получить переменную кадра по ее имени. (Внесено Виктором Стиннером в gh-91248).

  • Добавьте PyErr_GetRaisedException() и PyErr_SetRaisedException() для сохранения и восстановления текущего исключения. Эти функции возвращают и принимают один объект исключения, а не тройной аргумент в уже устаревших PyErr_Fetch() и PyErr_Restore(). Это меньше подвержено ошибкам и немного эффективнее. (Внесено Марком Шенноном в gh-101578).

  • Добавьте _PyErr_ChainExceptions1, который принимает экземпляр исключения, чтобы заменить legacy-API _PyErr_ChainExceptions, который теперь устарел. (Внесено Марком Шенноном в gh-101578).

  • Добавьте PyException_GetArgs() и PyException_SetArgs() в качестве удобных функций для получения и изменения args, переданного конструктору исключения. (Внесено Марком Шенноном в gh-101578).

  • Добавьте PyErr_DisplayException(), который принимает экземпляр исключения, чтобы заменить legacy-api PyErr_Display(). (Внесено Ирит Катриэль в gh-102755).

  • PEP 683: Вводятся бессмертные объекты, позволяющие объектам обходить счетчики ссылок, и связанные с этим изменения в C-API:

    • _Py_IMMORTAL_REFCNT: Количество ссылок, определяющих объект

      как бессмертный.

    • _Py_IsImmortal Проверяет, есть ли у объекта бессмертный счетчик ссылок.

    • PyObject_HEAD_INIT Теперь счетчик ссылок будет инициализирован до значения

      _Py_IMMORTAL_REFCNT при использовании с Py_BUILD_CORE.

    • SSTATE_INTERNED_IMMORTAL Идентификатор для интернированных объектов юникода

      которые бессмертны.

    • SSTATE_INTERNED_IMMORTAL_STATIC Идентификатор для интернированного юникода

      бессмертные и статичные объекты

    • sys.getunicodeinternedsize Возвращается общее количество юникода

      объекты, которые были интернированы. Теперь это необходимо для того, чтобы refleak.py правильно отслеживал количество ссылок и выделенных блоков

    (Предоставлено Эдди Элизондо в gh-84436).

  • PEP 684: Добавьте новую функцию Py_NewInterpreterFromConfig() и PyInterpreterConfig, которые можно использовать для создания подинтерпретаторов с собственными GIL. (См. PEP 684: Пер-интерпретатор GIL для получения дополнительной информации.) (Внесено Эриком Сноу в gh-104110).

  • В ограниченном API C версии 3.12 функции Py_INCREF() и Py_DECREF() теперь реализованы как непрозрачные вызовы функций, чтобы скрыть детали реализации. (Внесено Виктором Стиннером в gh-105387).

Переход на Python 3.12

  • Устаревшие API, основанные на представлении Юникода Py_UNICODE*, были удалены. Пожалуйста, перейдите на API, основанные на UTF-8 или wchar_t*.

  • Функции разбора аргументов, такие как PyArg_ParseTuple(), больше не поддерживают формат, основанный на Py_UNICODE* (например, u, Z). Пожалуйста, перейдите на другие форматы для Юникода, такие как s, z, es и U.

  • tp_weaklist для всех статических встроенных типов всегда становится NULL. Это поле только для внутреннего использования в PyTypeObject, но мы указываем на это изменение на случай, если кто-то все равно будет обращаться к этому полю напрямую. Чтобы избежать поломок, используйте вместо этого существующий общедоступный C-API или, при необходимости, макрос _PyObject_GET_WEAKREFS_LISTPTR() (только для внутреннего использования).

  • Теперь этот внутренний указатель PyTypeObject.tp_subclasses может не быть корректным указателем объекта. Его тип был изменен на void*, чтобы отразить это. Мы упомянули об этом на случай, если кто-то обратится к полю, предназначенному только для внутреннего использования, напрямую.

    Чтобы получить список подклассов, вызовите метод Python __subclasses__() (например, используя PyObject_CallMethod()).

  • Добавьте поддержку дополнительных опций форматирования (выравнивание по левому краю, восьмеричные числа, прописные шестнадцатеричные числа, intmax_t, ptrdiff_t, wchar_t) в PyUnicode_FromFormat() и PyUnicode_FromFormatV(). C-строки, переменная ширина и точность) в PyUnicode_FromFormat() и PyUnicode_FromFormatV(). (Внесено Сергеем Сторчакой в gh-98836).

  • Нераспознанный символ формата в PyUnicode_FromFormat() и PyUnicode_FromFormatV() теперь устанавливает SystemError. В предыдущих версиях это приводило к тому, что вся остальная часть строки формата копировалась в строку результата как есть, а лишние аргументы отбрасывались. (Внесено Сергеем Сторчакой в gh-95781).

  • Исправьте неправильное расположение знаков в PyUnicode_FromFormat() и PyUnicode_FromFormatV(). (Внесено Филипом Георги в gh-95504).

  • Классы расширений, желающие добавить слот __dict__ или слабую ссылку, должны использовать Py_TPFLAGS_MANAGED_DICT и Py_TPFLAGS_MANAGED_WEAKREF вместо tp_dictoffset и tp_weaklistoffset соответственно. Использование tp_dictoffset и tp_weaklistoffset по-прежнему поддерживается, но не полностью поддерживает множественное наследование (gh-95589), и производительность может быть хуже. Классы, объявляющие Py_TPFLAGS_MANAGED_DICT, должны вызывать _PyObject_VisitManagedDict() и _PyObject_ClearManagedDict() для обхода и очистки словарей своих экземпляров. Для очистки слабых ссылок, как и раньше, вызывайте PyObject_ClearWeakRefs().

  • Функция PyUnicode_FSDecoder() больше не принимает байтовые пути, такие как типы bytearray и memoryview: для байтовых строк принимается только точный тип bytes. (Внесено Виктором Стиннером в gh-98393).

  • Макросы Py_CLEAR, Py_SETREF и Py_XSETREF теперь оценивают свои аргументы только один раз. Если аргумент имеет побочные эффекты, то эти побочные эффекты больше не дублируются. (Внесено Виктором Стиннером в gh-98724).

  • Индикатор ошибки интерпретатора теперь всегда нормализован. Это означает, что PyErr_SetObject(), PyErr_SetString() и другие функции, устанавливающие индикатор ошибки, теперь нормализуют исключение перед его сохранением. (Внесено Марком Шенноном в gh-101578).

  • _Py_RefTotal больше не является авторитетным и сохраняется только для совместимости с ABI. Обратите внимание, что он является внутренним глобальным и доступен только в отладочных сборках. Если вы случайно используете его, то вам нужно начать использовать _Py_GetGlobalRefTotal().

  • Следующие функции теперь выбирают подходящий метакласс для вновь созданного типа:

    Создание классов, чей метакласс переопределяет tp_new, является устаревшим, и в Python 3.14+ оно будет запрещено. Обратите внимание, что эти функции игнорируют tp_new метакласса, что может привести к неполной инициализации.

    Обратите внимание, что PyType_FromMetaclass() (добавлен в Python 3.12) уже запрещает создавать классы, чей метакласс переопределяет tp_new (__new__() в Python).

    Поскольку tp_new переопределяет почти все функции PyType_From*, они несовместимы друг с другом. Существующее поведение - игнорирование метакласса на нескольких этапах создания типа - в целом небезопасно, поскольку (мета)классы предполагают, что tp_new был вызван. Простого общего обходного пути не существует. Возможно, вам подойдет один из следующих вариантов:

    • Если вы управляете метаклассом, избегайте использования в нем tp_new:

      • Если инициализацию можно пропустить, она может быть выполнена в tp_init.

      • Если метакласс не нужно инстанцировать из Python, установите его tp_new в NULL с помощью флага Py_TPFLAGS_DISALLOW_INSTANTIATION. Это сделает его допустимым для функций PyType_From*.

    • Избегайте PyType_From* функций: если вам не нужны специфические для C возможности (слоты или установка размера экземпляра), создавайте типы с помощью calling метакласса.

    • Если вы знаете, что tp_new можно безопасно пропустить, отфильтруйте предупреждение об устаревании, используя warnings.catch_warnings() из Python.

  • PyOS_InputHook и PyOS_ReadlineFunctionPointer больше не вызываются в subinterpreters. Это связано с тем, что клиенты обычно полагаются на глобальное состояние всего процесса (поскольку эти обратные вызовы не имеют возможности восстановить состояние модуля расширения).

    Это также позволяет избежать ситуаций, когда расширения могут оказаться запущенными в подинтерпретаторе, который они не поддерживают (или в который они еще не были загружены). Дополнительную информацию см. в разделе gh-104668.

  • Внутренние компоненты PyLongObject были изменены для повышения производительности. Хотя внутренние поля PyLongObject являются приватными, они используются некоторыми модулями расширения. К внутренним полям больше не следует обращаться напрямую, вместо этого следует использовать API-функции, начинающиеся с PyLong_.... Две новые нестабильные API-функции предназначены для эффективного доступа к значениям PyLongObject, которые помещаются в одно машинное слово:

  • Пользовательские аллокаторы, задаваемые через PyMem_SetAllocator(), теперь обязаны быть потокобезопасными, независимо от домена памяти. Аллокаторы, не имеющие собственного состояния, включая «крючки», не затрагиваются. Если ваш пользовательский аллокатор еще не является потокобезопасным и вам нужны рекомендации, создайте новый вопрос на GitHub и CC @ericsnowcurrently.

Утратившие актуальность

Удаление ожиданий в Python 3.14

Удаление ожиданий в Python 3.15

Ожидается удаление в будущих версиях

Следующие API устарели и будут удалены, хотя в настоящее время дата их удаления не назначена.

Удалено

  • Удалите заголовочный файл token.h. Публичного API токенизатора на C никогда не существовало. Заголовочный файл token.h был предназначен только для использования внутренними модулями Python. (Внесено Виктором Стиннером в gh-92651).

  • Устаревшие API Unicode были удалены. Подробности см. в разделе PEP 623.

    • PyUnicode_WCHAR_KIND

    • PyUnicode_AS_UNICODE()

    • PyUnicode_AsUnicode()

    • PyUnicode_AsUnicodeAndSize()

    • PyUnicode_AS_DATA()

    • PyUnicode_FromUnicode()

    • PyUnicode_GET_SIZE()

    • PyUnicode_GetSize()

    • PyUnicode_GET_DATA_SIZE()

  • Удалите макрос функции PyUnicode_InternImmortal(). (Внесено Виктором Стиннером в gh-85858).