美文网首页Pythonpython编程
浅淡python中with的用法,上下文管理器

浅淡python中with的用法,上下文管理器

作者: 成功在于实践 | 来源:发表于2019-07-30 21:47 被阅读14次

    https://www.cnblogs.com/huchong/p/8268765.html

    上下文管理器

    任何实现了 enter() 和 exit() 方法的对象都可称之为上下文管理器,上下文管理器对象可以使用 with 关键字。显然,文件(file)对象也实现了上下文管理器。

    那么文件对象是如何实现这两个方法的呢?我们可以模拟实现一个自己的文件类,让该类实现 enter() 和 exit() 方法。

    class File():
    
        def __init__(self, filename, mode):
            self.filename = filename
            self.mode = mode
    
        def __enter__(self):
            print("entering")
            self.f = open(self.filename, self.mode)
            return self.f
    
        def __exit__(self, *args):
            print("will exit")
            self.f.close()
    

    enter() 方法返回资源对象,这里就是你将要打开的那个文件对象,exit() 方法处理一些清除工作。

    因为 File 类实现了上下文管理器,现在就可以使用 with 语句了。

    with File('out.txt', 'w') as f:
        print("writing")
        f.write('hello, python')
    

    这样,你就无需显示地调用 close 方法了,由系统自动去调用,哪怕中间遇到异常 close 方法也会被调用。

    实现上下文管理器的另外方式

    Python 还提供了一个 contextmanager 的装饰器,更进一步简化了上下文管理器的实现方式。通过 yield 将函数分割成两部分,yield 之前的语句在 enter 方法中执行,yield 之后的语句在 exit 方法中执行。紧跟在 yield 后面的值是函数的返回值。

    from contextlib import contextmanager
    
    @contextmanager
    def my_open(path, mode):
        f = open(path, mode)
        yield f
        f.close()
    

    调用

    with my_open('out.txt', 'w') as f:
        f.write("hello , the simplest context manager")
    

    总结

    Python 提供了 with 语法用于简化资源操作的后续清除操作,是 try/finally 的替代方法,实现原理建立在上下文管理器之上。此外,Python 还提供了一个 contextmanager 装饰器,更进一步简化上下管理器的实现方式。

    拓展文章:

    1.浅淡python中with的用法,上下文管理器

    https://www.cnblogs.com/huchong/p/8268765.html

    (1) 当with遇到上下文管理器,就会在执行语句体之前,先执行上下文管理器的enter方法,然后再执行语句体,执行完语句体后,最后执行exit方法

    (2) 使用了 with 语句,不管在处理文件过程中是否发生异常,都能保证 with 语句执行完毕后已经关闭了打开的文件句柄

    (3)调用上下文管理器的 enter 方法时;如果使用了 as 子句,则将 enter() 方法的返回值赋值给 as 子句中的目标

    with 上下文管理器  as  target:
       代码语句体
    

    with后面必须跟一个上下文管理器,如果使用了as,则是把上下文管理器的 enter() 方法的返回值赋值给 target,target 可以是单个变量,或者由“()”括起来的元组(不能是仅仅由“,”分隔的变量列表,必须加“()”)

    (4) 出现异常时,如果 exit 返回 False(默认不写返回值时,即为False),则会重新抛出异常,让with 之外的语句逻辑来处理异常,这也是通用做法;如果返回 True,则忽略异常,不再对异常进行处理

    (5)with只能配合上下文管理器使用,常见的上下文管理器有

    file
    decimal.Context
    thread.LockType
    threading.Lock
    threading.RLock
    threading.Condition
    threading.Semaphore
    threading.BoundedSemaphore
    

    2. with上下文管理器

    https://www.cnblogs.com/menkeyi/p/7130978.html

    contextlib 模块

    contextlib 模块提供了3个对象:装饰器 contextmanager、函数 nested 和上下文管理器 closing。使用这些对象,可以对已有的生成器函数或者对象进行包装,加入对上下文管理协议的支持,避免了专门编写上下文管理器来支持 with 语句。

    装饰器 contextmanager

    contextmanager 用于对生成器函数进行装饰,生成器函数被装饰以后,返回的是一个上下文管理器,其 enter() 和 exit() 方法由 contextmanager 负责提供,而不再是之前的迭代子。被装饰的生成器函数只能产生一个值,否则会导致异常 RuntimeError;产生的值会赋值给 as 子句中的 target,如果使用了 as 子句的话。

    3.上下文管理器

    https://blog.csdn.net/weixin_38853600/article/details/82887907

    相关文章

      网友评论

        本文标题:浅淡python中with的用法,上下文管理器

        本文链接:https://www.haomeiwen.com/subject/reworctx.html