Как избежать ошибки NameEr при создании псевдонима для типа аннотации с использованием циклической ссылки? - PullRequest
0 голосов
/ 28 марта 2019

Как показывает этот замечательный ответ , начиная с Python 3.7 и далее можно использовать предварительные объявления в аннотациях типов, если

from __future__ import annotations

используется инструкция.

Однако это все равно не работает, если я хочу создать псевдоним для типа аннотации:

from __future__ import annotations
import typing

MyType1 = typing.Union[str, MyType2]
MyType2 = typing.Mapping[str, MyType1]

Это все еще дает мне NameError: name 'MyType2' is not defined

Я знаю о запасном синтаксисе с использованием строковых литералов, и он работает. Однако мне любопытно, возможно ли каким-либо образом использовать официально доступный новый подход.

1 Ответ

0 голосов
/ 03 апреля 2019

Один из методов - использовать typing.TYPE_CHECKING константу . Эта константа всегда ложна во время выполнения, но обрабатывается так, как если бы она всегда была истинной с помощью средств проверки типов, таких как mypy:

from __future__ import annotations
from typing import TYPE_CHECKING, Union, Mapping
if TYPE_CHECKING:
    MyType1 = Union[str, MyType2]
    MyType2 = Mapping[str, MyType1]

Поскольку эта константа имеет значение False во время выполнения, Python никогда не будет пытаться оценить псевдоним любого типа, что позволяет избежать ошибки NameError.

Вам нужно будет либо использовать директиву from __future__ import annotations, либо использовать строковые литеральные типы всякий раз, когда вы, конечно, используете любой тип подсказки.

...