我有以下类用一个额外的DelegatorParent类实现“委托设计模式”:
class DelegatorParent():
def __init__(self):
self.a = 'whatever'
class ConcreteDelegatee():
def myMethod(self):
return 'myMethod'
class Delegator(DelegatorParent):
def __init__(self):
self.delegatee = ConcreteDelegatee()
DelegatorParent.__init__(self)
def __getattr__(self, attrname):
return getattr(self.delegatee, attrname)
a = Delegator()
result = a.myMethod()
一切看起来都很好。在
现在我想在DelegatorParent中放置一个抽象方法,以确保“myMethod”始终被定义。在
^{pr2}$你能帮我找到一个“优雅”的方法把“myMethod”从“Delegator”中删除。。。直觉告诉我它在某种程度上是多余的(考虑到定义了一个自定义getattr方法)。在
更重要的是,请注意,在这个实现中,如果我忘记在ConcreteDelegate中定义myMethod,程序将编译,但如果我调用它,它可能会在运行时崩溃委托人.myMethod(),这正是我想通过在DelegatorParent中使用抽象方法来避免的。在
显然,一个简单的解决方案是将@abstractmethod移到Delegator类,但我不想这样做,因为在我的程序中DelegatorParent是一个非常重要的类(Delegator只是一个辅助类)。在
这是我目前的解决方案。它解决了主要的问题(防止具体的delegate忘记定义myMethod),但我还是不太相信,因为我仍然需要在Delegator中定义myMethod,这似乎是多余的
您可以决定自动实现委派给
ConcreteDelegatee
的抽象方法。在对于每个抽象方法,检查其名称是否存在于
ConcreteDelegatee
类中,并将此方法作为该类方法的委托实现。在这解决了主要问题(防止})。如果您忘记了实现其他抽象方法,它们仍然会被检查。在
ConcreteDelegatee
忘记定义{__new__
方法负责委派,它可以释放您的__init__
来完成它。在由于使用
ABCMeta
,因此必须定义抽象方法。可以从__abstractmethods__
集中删除您的方法,但它是frozenset
。不管怎样,它包括列出所有抽象方法。在因此,您可以使用一个简单的描述符来代替
__getattr__
。在例如:
这里的一个优点是:开发人员拥有“myMethod”被委托的明确信息。在
如果您尝试:
^{pr2}$它起作用了!但是,如果您忘记在
Delegator
类中实现myMethod
,则会出现典型错误:编辑
这种实现可以概括如下:
在这里,我们可以指定delegatee名称和delegatee方法。在
相关问题 更多 >
编程相关推荐