获取修饰的类方法的类名

Pau*_*tas 5 python decorator

考虑这种情况:

import functools

def wrapmethod(f):
    @functools.wraps(f)
    def wrap(*args, **kwargs):
        print '>> %s' % (f.func_name)

        # Here I'll do pre-processing
        r = f(*args, **kwargs)
        # Here I'll do post-processing

        return r

    return wrap

@wrapmethod
def foo():
    pass

class Test(object):
    @wrapmethod
    def foo(self):
        pass

test = Test()
test.foo()
foo()
Run Code Online (Sandbox Code Playgroud)

如您在http://codepad.org/Y4xXyjJO中看到的那样,它将输出此内容:

>>富
>>富

我想知道一种Test.foo在第一行中打印出来的方法,指明该方法链接到的类。

有任何想法吗?有可能吗?

先感谢您。

SED*_*dji 10

实际上,您可以使用inspect模块来获取函数的签名,并且假设您遵循通过第一个参数'self'引用类对象的约定,您可以执行以下操作:

import inspect  
def print_name(*_args):
    def _print_name(fn):
        def wrapper(*args, **kwargs):
            try :
                is_method   = inspect.getargspec(fn)[0][0] == 'self'
            except :
                is_method   = False

            if is_method :
                name    = '{}.{}.{}'.format(fn.__module__, args[0].__class__.__name__, fn.__name__)
            else :
                name    = '{}.{}'.format(fn.__module__, fn.__name__)

            print (name)
            return  fn(*args,**kwargs)
        return wrapper
    return _print_name
Run Code Online (Sandbox Code Playgroud)

如果这是一个函数,这将打印方法模块、类和名称或仅打印模块和名称

从 python 3.3 开始,fn.__qualname__可用于获取函数/方法的限定名称。

def print_name(*args):
     def _print_name(fn):
         def wrapper(*args, **kwargs):
             print('{}.{}'.format(fn.__module__, fn.__qualname__))
             return fn(*args, **kwargs)
         return wrapper
     return _print_name
Run Code Online (Sandbox Code Playgroud)

这适用于函数和方法:

In [1]: class A():
...:     @print_name()
...:     def a():
...:         print('Hi from A.a')
In [2]: A.a()
    __main__.A.a
    Hi from A.a

In [25]: @print_name()
    ...: def b():
    ...:     print('Hi from b')
    ...: 
In [26]: b()
    __main__.b
    Hi from b
Run Code Online (Sandbox Code Playgroud)