【问题标题】:Decorating a class method装饰类方法
【发布时间】:2014-11-16 17:10:19
【问题描述】:

我想装饰一个类方法,但不知道该怎么做。最小类示例:

class Circle(object):
    def __init__(self,radius):
        self.R = radius

    def arc_length(self,theta):
        return self.R*theta

现在假设我想要另一种方法,它总是采用相对于弧长的某个特定其他值的 arc_length,所以我定义一个函数如下:

def relative(rel_val):
    def decorator(fn):
        def wrapper(*args):
            return fn(*args) - fn(rel_val)
        return wrapper
    return decorator

所以现在我将我的课程扩展到:

class Circle(object):
    def __init__(self,radius):
        self.R = radius

    def arc_length(self,theta):
        return self.R*theta

    @relative(0.2)
    def relative_arc_length(self,theta):
        return self.arc_length(theta)

我希望这会提供所需的行为,但我收到错误: relative_arc_length() 只需要 2 个参数(给定 1 个)

我认为这与 self 参数有关,但如果我将 self 添加到相对定义中的 fn(self,rel_val) 中,它会给我:全局名称“self”未定义

那么我该如何解决这个问题?有趣的是,如果我执行以下操作:

c = Circle(10)
relative(0.2)(c.arc_length)(1.5)

它按预期工作。

谁能指出我哪里出错了?另外,是否可以在类中定义装饰函数,如果可以,我应该这样做吗?这是良好的编程习惯吗?

【问题讨论】:

    标签: python class decorator


    【解决方案1】:
    return fn(*args) - fn(rel_val)
    

    总是以self 作为第一个参数调用方法。因此,在您的情况下,您将所有参数都传递给第一次调用,但忘记了第二次调用中的 self

    您必须从 args 中提取 self 并传递它:

    obj, value = args
    return fn(obj, value) - fn(obj, rel_value)
    

    您可能应该包括一个检查以确保在任何时候args 中只有两个值,因此您不会意外地将装饰器用于不兼容的方法。

    【讨论】:

      猜你喜欢
      • 2014-01-14
      • 2020-01-11
      • 1970-01-01
      • 1970-01-01
      • 2014-12-07
      • 2013-05-23
      • 1970-01-01
      • 2011-08-25
      • 2019-11-06
      相关资源
      最近更新 更多