Является ли Type [тип] правильной подсказкой типа для объекта класса? - PullRequest
0 голосов
/ 30 апреля 2018

Мой вопрос: правильно ли мое использование AnyType (как я определил его ниже)? Цель состоит в том, чтобы AnyType мог принять любой объект класса, но экземпляры объектов класса, или типов функций, или других вещей, не относящихся к типу type, должны быть отклонены.

подробности:

У меня есть класс, который выглядит примерно так:

MixinSubclsType = Type["ChildRegistryMixin"]
AnyType = Type[type] # <- is this correct?

class ChildRegistryMixin:
    """Mixin class that creates classes which track subclasses.

    Each new child class will track its own children."""
    _subclasses: Dict[Any, MixinSubclsType] = dict()
    _make_reg_key: Callable[[AnyType], Any]] = lambda subcls: getattr(subcls, "__name__")
    def __init_subclass__(subcls,
                          make_reg_key: Optional[Callable[[AnyType], Any]]] = None,
                          **kwargs) -> None:
        # implementation here

Является ли Type[type] правильным способом сказать контролеру типов, что lambda должен принимать только объекты класса?


Поскольку больше информации иногда лучше, чем меньше, ниже приведена вся реализация.

class ChildRegistryMixin:
    """Mixin class that creates classes which track subclasses.

    Each new child class will track its own children.

    Usage example 1:

        class RegisteredByName(ChildRegistryMixin): ...

        assert ChildRegistryMixin._subclasses["RegisteredByName"] is RegisteredByName

    Usage example 2:

        valid_lookup = dict(ClassName="othername")

        class RegisteredByPop(ChildRegistryMixin,
                              make_reg_key=lambda subcls:
                                           valid_lookup.pop(subcls.__name__)):
            pass

        class ClassName(RegisteredByPop): ...

        assert RegisteredByPop._subclasses["othername"] is ClassName

        class InvalidName(RegisteredByPop): ... # <-- ERROR!

    """
    _subclasses: Dict[Any, MixinSubclsType] = dict()
    _make_reg_key: Callable([AnyType], Any) = lambda subcls: getattr(subcls, "__name__")
    def __init_subclass__(subcls,
                          make_reg_key: Optional[Callable([AnyType], Any)] = None,
                          **kwargs) -> None:
        super().__init_subclass__(**kwargs)
        # for later child classes of the new class
        subcls._subclasses = dict()
        # child added to the reg of closest parent that is a subclass of CRB
        for parent_cls in subcls.mro()[1:]:
            if issubclass(parent_cls, ChildRegistryMixin):
                break
        else:
            parent_cls = ChildRegistryMixin
        # make the key
        key = parent_cls._make_reg_key(subcls)
        # can't have multiple child classes with same key
        if key not in parent_cls._subclasses:
            parent_cls._subclasses[key] = subcls
        else:
            raise ChildRegistryError(f"Attempted to overwrite the "
                                     f"child class key {key!r} in the "
                                     f"{parent_cls.__name__} registry")
        # inherit the subclass' key maker from parent if one was not provided
        subcls._make_reg_key = parent_cls._make_reg_key if make_reg_key is None\
                                                        else make_reg_key
...