繁体   English   中英

可继承的跟踪装饰器

[英]Inheritable Tracking Decorator

我需要一个带有内部定义的装饰器的父类,该装饰器将其类中的所有函数保存到列表中,该列表是父类的属性。 此类的所有子级必须能够使用装饰器,但必须存储到特定子级拥有的列表中。

在多次尝试定义这样的装饰器之后,我对如何完成工作一无所知。 任何帮助将不胜感激! 我的首选用法示例如下所示。

class Parent:
    decorated_functions = []

    # insert decorator definition

class ChildOne(Parent):
    @decorator
    def a(self):
        return 'a'

    @decorator
    def b(self):
        return 'b'

class ChildTwo(Parent):
    @decorator
    def c(self):
        return 'c'

class ChildThree(Parent):
    @decorator
    def d(self):
        return 'd'

    @decorator
    def e(self):
        return 'e'

    @decorator
    def f(self):
        return 'f'

ChildOne().decorated_functions
# [<function __main__.ChildOne.a>, <function __main__.ChildOne.b>]

ChildTwo().decorated_functions
# [<function __main__.ChildTwo.c>]

ChildThree().decorated_functions
# [<function __main__.ChildThree.d>, <function __main__.ChildThree.e>, <function __main__.ChildThree.f>]

更新#1使用Brendan Abel的元类,我尝试使用以下代码。

class Child(Parent):
    @decorator
    def a(self):
        return 'a'

    @decorator
    def b(self):
        return 'b'

print(Child().decorated_functions)

但是, Child()似乎没有decorated_functions的属性。

AttributeError: type object 'Child' has no attribute 'decorated_functions'

更新#2上面的代码现在可以与Brendan Abel的解决方案一起使用! 问题是元类Python 3的语法发生了变化。

如果不将decorated_functions转换为属性(允许在创建类之后进行计算)或使用类装饰器或元类,则可能无法执行此操作。 我从没想过要这么说,但是元类可能是这里最简单的解决方案

def decorator(f):
    f.decorated = True
    return f


class DecoMeta(type):

    def __new__(cls, name, bases, attrs):
        decorated_functions = []
        for v in attrs.values():
            if getattr(v, 'decorated', None):
                decorated_functions.append(v)
        attrs['decorated_functions'] = decorated_functions
        return super(DecoMeta, cls).__new__(cls, name, bases, attrs)


class Parent(object):
    __metaclass__ = DecoMeta

编辑:

在Python 3中,元类挂钩略有不同

class Parent(object, metaclass=DecoMeta):
    ...

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM