Class abstract/static 类 的实例化和变量共享

Class Instantiation, and variable sharing for abstract/static classes

我的问题的简单示例:

class AbstractService:
    subscribers = []

    @classmethod
    def subscribe(cls, service):
        service.subscribers.append(cls)

    @classmethod
    @abstractmethod
    def notify(cls, payload):
        raise NotImplementedError(f"{cls.__name__} not implemented notify()")


class ServiceA(AbstractService):

    @classmethod
    def notify(cls, payload):
        pass


class ServiceB(AbstractService):

    @classmethod
    def notify(cls, payload):
        pass


ServiceB.subscribe(ServiceA)

ServiceA.notify({'message': 'hello'})

问题是这个实例中的所有服务都将共享订阅者,因此我的解决方案是创建一个函数,returns 抽象服务本身:


def get_abstract_service():
        
    class AbstractService:
        subscribers = []
    
        @classmethod
        def subscribe(cls, service):
            service.subscribers.append(cls)
    
        @classmethod
        @abstractmethod
        def notify(cls, payload):
            raise NotImplementedError(f"{cls.__name__} not implemented notify()")

    return AbstractService
class ServiceA(get_abstract_service()):

    @classmethod
    def notify(cls, payload):
        pass


class ServiceB(get_abstract_service()):

    @classmethod
    def notify(cls, payload):
        pass


ServiceB.subscribe(ServiceA)

ServiceA.notify({'message': 'hello'})

这现在可以工作了,因为每个订阅者都是唯一的 class 继承抽象服务。

问题

  1. 这对 python 是否正确,或者模式是否错误,如果是这样会是什么 这种情况下的常态

  2. 如果我的解决方案是正确的,我该如何处理 AbstractService 的输入 (对于任何需要将该类型传递给它的函数)

我会这样处理:

from __future__ import annotations


class AbstractService:
    subscribers: list[AbstractService]

    def __init_subclass__(cls, **kw):
        super().__init_subclass__(**kw)
        cls.subscribers = []

它在创建后的每个 class 上设置一个新的 subscribers 实例。

编辑:此外,它还可以使用 from __future__ import annotations

为您处理打字

例如

class C:
    def f(self) -> C:
        ...