当前位置: 首页 > 面试题库 >

Python装饰器使函数忘记它属于一个类

胥良平
2023-03-14
问题内容

我试图写一个装饰器来记录日志

def logger(myFunc):
    def new(*args, **keyargs):
        print 'Entering %s.%s' % (myFunc.im_class.__name__, myFunc.__name__)
        return myFunc(*args, **keyargs)

    return new

class C(object):
    @logger
    def f():
        pass

C().f()

我想打印:

Entering C.f

但相反,我收到此错误消息:

AttributeError: 'function' object has no attribute 'im_class'

大概这与’logger’中’myFunc’的范围有关,但是我不知道是什么。


问题答案:

Claudiu的答案是正确的,但是您也可以通过从self参数中删除类名来作弊。在继承的情况下,这将产生误导性的日志语句,但会告诉您正在调用其方法的对象的类。例如:

from functools import wraps  # use this to preserve function signatures and docstrings
def logger(func):
    @wraps(func)
    def with_logging(*args, **kwargs):
        print "Entering %s.%s" % (args[0].__class__.__name__, func.__name__)
        return func(*args, **kwargs)
    return with_logging

class C(object):
    @logger
    def f(self):
        pass

C().f()

就像我说的那样,如果您从父类继承了一个函数,这将无法正常工作。在这种情况下,您可能会说

class B(C):
    pass

b = B()
b.f()

并获取消息Entering B.fEntering C.f因为那是正确的类,所以您实际上希望在其中获取消息。另一方面,这可能是可以接受的,在这种情况下,我会建议这种方法胜过Claudiu的建议。



 类似资料:
  • 主要内容:带参数的函数装饰器,函数装饰器可以嵌套前面章节中,我们已经讲解了 Python 内置的 3 种函数装饰器,分别是 @staticmethod、@classmethod 和 @property,其中 staticmethod()、classmethod() 和 property() 都是 Python 的内置函数。 那么,函数装饰器的工作原理是怎样的呢?假设用 funA() 函数装饰器去装饰 funB() 函数,如下所示: 实际上,上面

  • 问题内容: 我已经看到许多Python装饰器的示例,它们是: 函数样式修饰符(包装函数) 类风格装饰(实施,和) 不带参数的装饰器 带参数的装饰器 “方法友好”的装饰器(即可以装饰类中的方法) “功能友好”的装饰器(可以装饰普通功能 可以装饰方法和功能的装饰器 但是我从未见过一个可以完成上述所有操作的示例,而且我无法从各种答案到特定问题,这个或这个上看到过,如何结合以上所有内容。 我想要的是一个

  • rank ▲ ✰ vote url 3 1346 1485 2648 url Python中如何在一个函数中加入多个装饰器? 怎么做才能让一个函数同时用两个装饰器,像下面这样: @makebold @makeitalic def say(): return "Hello" 我希望得到 <b><i>Hello</i></b> 我只是想知道装饰器怎么工作的! 去看看文档,答在下面: def

  • 问题内容: 我想定义一些通用装饰器,以在调用某些函数之前检查参数。 就像是: 旁注: 类型检查只是在这里显示一个示例 我正在使用Python 2.7,但是Python 3.0也会很有趣 问题答案: 从装饰器的功能和方法: Python 2 Python 3 在Python 3中已更改为,并且已更改为。 用法: 可以是或

  • 问题内容: 有没有办法像python风格那样装饰C ++中的函数或方法? 例如,使用宏: 要么 可能吗? 问题答案: 提供了我提出的解决方案的大多数构建块。 这是我建议的解决方案。 输出: ps 提供了一个可以进行功能调用以外的其他功能的地方。如果您想简单地传递至,可以使用:

  • 问题内容: 我想这就是它们的称呼,但我会举一些例子以防万一。 装饰类: 装饰器功能: 使用一个或另一个只是口味的问题吗?有实际区别吗? 问题答案: 如果您可以编写函数来实现装饰器,则应首选它。但是并非所有装饰器都可以轻松地编写为一个函数-例如,当您要存储一些内部状态时。 我见过人们(包括我自己)经过荒唐的努力,只用函数编写装饰器。我仍然不知道为什么,一个班级的开销通常可以忽略不计。