代码之家  ›  专栏  ›  技术社区  ›  spencer

为什么有必要将self作为方法装饰器的参数?

  •  4
  • spencer  · 技术社区  · 7 年前

    def dec(f):
        def wrap(*args, **kwargs):
            f(*args, **kwargs)
        return wrap
    
    @dec
    def foo(arg1):
        pass
    

    然而,当装饰方法时,突然之间你必须有一个参数来捕捉实例。

    def dec(f):
        def wrap(self, *args, **kwargs):
            f(self, *args, **kwargs)
        return wrap
    
    
    class Test:
        def __init__(self):
            pass
    
        @dec
        def foo(self, arg1):
            pass
    

    为什么会这样?有什么特别的 self *args 不能抓住它吗?毕竟,这不只是另一个立场论点吗? )传递到内部 wrap 作用

    foo = dec(foo) .根据我之前对闭包的了解 foo __closure__ .

    似乎不属于 __关闭__ ?

    2 回复  |  直到 7 年前
        1
  •  3
  •   NPE    7 年前

    为什么会这样?有什么特别的 self 那个 *args 不能抓住它吗?

    *args 可以包括

    没有装饰器:

    class Test(object):
    
      def foo(self, *args):
        return (self,) + args
    
      def bar(*args):  # for the purposes of illustration
        return args
    
    t = Test()
    print(t.foo(42))
    print(t.bar(42))
    

    def dec(f):
        def wrap(*args, **kwargs):
            return f(*args, **kwargs)
        return wrap
    
    class Test(object):
    
        @dec
        def foo(self, arg1):
            return (self, arg1)
    
    t = Test()
    print(t.foo(42))
    
        2
  •  0
  •   David Duffrin    7 年前

    我认为Python的创造者自己说得最好:

    http://neopythonic.blogspot.com/2008/10/why-explicit-self-has-to-stay.html

    主要两点是:

    在参数列表中保留显式“self”的另一个理由是,可以通过插入函数来动态修改类,从而创建相应的方法。