Когда на самом деле Python выполняет декораторы?

Когда на самом деле Python выполняет декораторы?

Главное свойство декораторов — то, что они выполняются сразу после определения декорируемой функции. Обычно на этапе импорта то есть когда Python загружает модуль.

Рассмотрим скрипт registration.py в примере №1.

Пример №1. Модуль registration.py

1. В registry хранятся ссылки на функции, декорированные @register.

2. register принимает функцию в качестве аргумента.

3. Показываем, какая функция декорируется — для демонстрации.

4. Включаем func в registry.

5. Возвращаем func: мы должны вернуть функцию, в данном случае возвращается та же функция, что была передана на входе.

6. f1 и f2 декорированы @register.

7. f3 не декорирована.

8. main распечатывает registry, затем вызывает f1(), f2() и f3().

9. main() вызывается только тогда, когда registration.py запускается как скрипт.

Будучи запущена как скрипт, программа registration.py выводит следующие строки:

Отметим, что register выполняется дважды до любой другой функции в модуле. При вызове register получает в качестве аргумента декорируемый объект-функцию, например <function f1 at 0x7f69ee2a07b8>.

После загрузки модуля в register оказываются ссылки на две декорированные функции: f1 и f2. Они, как и функция f3, выполняются только при явном вызове из main.

Если registration.py импортируется а не запускается как скрипт, то вывод выглядит так:

Если сейчас заглянуть в registry, то мы увидим:

Основная цель примера №1 — подчеркнуть, что декораторы функций выполняются сразу после импорта модуля, но сами декорируемые функции — только в результате явного вызова.

В этом проявляется различие между этапом импорта и этапом выполнения в Python.

Планирую внедрять промо-ролики-уроки Python с помощью Adobe After Effects. Сейчас много таких готовых роликов можно скачать на Hunterae.com. Например, можете взглянуть на проект Code Source.

По сравнению с типичным применением декораторов в реальных программах пример №1 необычен в двух отношениях:

  1. Функция декоратор определена в том же модуле, что и декорируемые функции. Настоящий декоратор обычно определяется в одном модуле и применяется к функциям из других модулей.
  2. Декоратор register возвращает ту же функцию, что была передана в качестве аргумента. На практике декоратор обычно определяет внутреннюю функцию и возвращает именно ее.

Хотя декоратор register из примера №1 возвращает декорированную функцию без изменения, эта техника не бесполезна.

Подобные декораторы используются во многих веб-фреймворков, написанных на Python, например Django и Flask, с целью добавления функций в некий центральный реестр, например, для отображения образцов URL на функции, генерирующие HTTP-ответы.

Такие регистрационные декораторы могут изменять декорируемую функцию, но это необязательно.

Советуем вам следующее видео к просмотру

PythonLearn

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *