Новые аннотации нарушают проверку классов данных - PullRequest
0 голосов
/ 04 сентября 2018

С помощью PEP 563 from __future__ import annotations изменяет аннотации типов так, чтобы они оценивались лениво, что обеспечивает множество преимуществ, таких как прямые ссылки.

Однако это плохо работает с другими функциями, такими как классы данных. Например, у меня есть некоторый код, который проверяет параметры типа метода класса __init__. (Реальный вариант использования - предоставить сериализатор по умолчанию для класса, но это здесь не важно.)

from dataclasses import dataclass
from typing import get_type_hints

class Foo:
    pass

@dataclass
class Bar:
    foo: Foo

print(get_type_hints(Bar.__init__))

В Python 3.6 и 3.7 это делает то, что ожидается; печатает {'foo': <class '__main__.Foo'>, 'return': <class 'NoneType'>}.

Однако, если в Python 3.7 я добавлю from __future__ import annotations, произойдет сбой с ошибкой:

NameError: name 'Foo' is not defined

Мне кажется, я понимаю, почему это происходит. Метод __init__ определен в dataclasses, который не имеет объекта Foo в своем окружении, а аннотация Foo передается в dataclass и присоединяется к __init__ в виде строки "Foo". чем исходный объект Foo, но get_type_hints для новых аннотаций выполняет поиск имени только в модуле, где __init__ определяется не там, где аннотация.

Мне кажется, что я что-то делаю не так. Я удивлен, что эти две новые функции играют так плохо вместе. Есть ли правильный способ проверки подсказок типа метода __init__, чтобы он работал с классами данных так же, как с обычными классами?

1 Ответ

0 голосов
/ 24 октября 2018

Когда сообщил в список рассылки Python, это считалось"хорошей добычей" со стороны BDFL. В соответствии с запросами и он должен работать, как ожидается, в Python 3.7.2 и более поздних версиях.

...