如何在decorator中使用上下文管理器,以及如何将在decorator中创建的对象传递给decorated函数

2024-10-02 02:36:50 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个测试类,需要在最后做一些清理。为了确保用户不会忘记这样做,我想在类中添加一个上下文管理器。我还有一个decorator,我想在里面使用这个上下文管理器来创建一个test类的对象并将它传递给修饰函数。有可能吗?在

这就是我要做的:

class test:
    def __init__(self, name):
        self._name = name
        print "my name is {0}".format(name)

    def exit():
        print "exiting"

    @contextmanager
    def testcm(self):
        print "inside cm"
        try:
            yield self
        finally:
            self.exit()

    def randomtest(self, str):
        print "Inside random test {0}".format(str)


def decorate(name):
    def wrapper(testf):
        def testf_wrapper(test):
            with test(name).testcm() as testobj:
                return testf(testobj)
            return testf_wrapper
        return wrapper
    return decorate

@decorate("whatever")
def testf(testobj):
    testobj.randomtest("randomness")

函数testf接受测试类对象testobj,并对其进行处理。之后,由于上下文管理器,testcm确保cleanup函数被调用。在

所以有两个问题:

  1. 我如何在decorator中使用上下文管理器,据我所知decorator必须返回一个函数,但是如果我返回函数(如上面的代码中所示),上下文管理器将如何调用cleanup?

  2. 我如何将在decorator中创建的对象传递给修饰函数,如果我像上面的代码一样传递它,我将如何调用修饰函数?


Tags: 对象函数nametestself管理器returndef
1条回答
网友
1楼 · 发布于 2024-10-02 02:36:50

您的示例程序中有几个错误,我在所有test/testf/testobj冗余中迷失了方向。请允许我直接回答你的问题。在

How do I use a context manager inside a decorator?

就像在其他地方使用上下文管理器一样。考虑这个程序,它在调用函数时使用修饰符将str透明地转换为file

def opener(func):
    def wrapper(name):
        with open(name) as input_file:
            func(input_file)
    return wrapper

@opener
def first_line(fd):
    print fd.readline()

first_line('/etc/passwd')

如您所见,decorator函数在调用修饰函数时使用上下文管理器。在

How do I pass an object created in decorator to the decorated function, if I pass it like in above code, how would I call the decorated function?

就像你把一个对象传递给任何函数一样。看我上面的例子。decorator创建一个file对象并将其传递给修饰函数。在


为了完整起见,下面是您的示例程序,其中错误已修复:

^{pr2}$

相关问题 更多 >

    热门问题