允许子类在python中指定他们想要装饰的方法

Posted

技术标签:

【中文标题】允许子类在python中指定他们想要装饰的方法【英文标题】:Allowing subclasses to designate which method they want to decorate with in python 【发布时间】:2013-06-24 01:11:09 【问题描述】:

我正在干燥一些具有类代码副本并粘贴的代码。我已将代码制成子类,以实现所需的不同元素,但代码的遗留问题之一是为一个通用命名的方法调用了特定于每个类的不同装饰器。

在这个例子中,它是foo 方法。 @some_decorator_function 曾经从每个类的另一个命名空间导入。现在装饰器只从父类调用一次,它不知道使用什么装饰器作为子类需要选择它。

有没有办法将装饰函数委托给子类?

我的想法(并立即提出NotImplementedError,因为 X 已评估):

class X:

  def some_decorator_function():
    raise NotImplementedError

  @some_decorator_function()
  def foo(self):
    return "Yo!"


def concrete_function(func):
  pass

class Y(X):
  def some_decorator_function():
    concrete_function

Y().foo

【问题讨论】:

【参考方案1】:

我认为最简单的方法是在 Y 中显式应用正确的装饰器:

class X:
    def foo(self):
        return "Yo!"

def concrete_function(func):
    pass

class Y(X):
    foo = concrete_function(X.foo)

Y().foo

【讨论】:

【参考方案2】:

您可以将装饰器转换为更通用的模式。

def class_defined_decorator(func):
    def wrapper(*args, **kwargs):
        return args[0]._decorator(func, *args, **kwargs)
    return wrapper

class Base(object):
    def _decorator(self, func, *args, **kwargs):
        raise NotImplementedError
    @class_defined_decorator
    def foo(self):
        pass

class Child(Base):
    def _decorator(self, func, *args, **kwargs):
        # Do decorator behavior
        return func(*args, **kwargs)

如果你必须支持使用相同的装饰器装饰静态、类和实例方法,你可以通过让装饰器返回一个描述符来获得更好的体验。

【讨论】:

以上是关于允许子类在python中指定他们想要装饰的方法的主要内容,如果未能解决你的问题,请参考以下文章

Python子类方法从超类方法继承装饰器

子类装饰方法的类型不兼容 - python

python继承简介

Python:如何使用父类中的方法装饰子类中的方法?

python中子类的装饰函数

如何装饰子类中的继承方法?