• Python上下文管理器 with


    对于系统资源的操作,如:文件操作、数据库操作等,我们往往打开文件、连接数据库后忘了将其close掉,这时就可能会引发异常,因此我们常用的做法是:

    # coding:utf-8
    
    f = open("a.txt", "w+")
    try:
        f.write("python")
    except IOError:
        print("IO ERR")
    finally:
        f.close()

    这段代码的确能解决实际问题,但是看起来有些繁琐冗余,因此Python引入了内置的with模块来简单优雅地解决此类问题。

    with open("a.txt", "w+") as f:
        f.write("with python")

    当执行到with代码块外的时候,系统会自动调用__exit__()方法,with替代了上述代码中的try-finally的功能,其原理是用到了上下文管理器。
    所谓的上下文管理器就是实现了 __enter__() 和 __exit__() 方法的对象:
    class ContextWith(object):
        def __enter__(self):
            print("执行__enter__方法")
    
        def __exit__(self, exc_type, exc_val, exc_tb):
            print("执行__exit__方法")
    
    
    def get_context():
        return ContextWith()
    
    
    with get_context() as f:
        print("执行with模块内")

    result:

      执行__enter__方法
      执行with模块内
      执行__exit__方法

    
    

    上面代码可以看出在执行with时会先调用__enter__方法,然后执行with模块内的,最后退出with模块时会调用__exit__方法,对于上下文管理器,

    Python中主要是contextlib模块,它是通过Generator实现的:

    contextlib模块主要有:

    • ContextDecorator:这是个基类,用于定义基于类的上下文管理器,同时也可以用@ContextDecorator作用于函数上。
    • contextmanager:运行上下文的对象,控制着运行上下文的功能,上下文管理器通常由 with 语句触发,也可以直接通过调用contextmanager方法来使用。
    • closing:创建上下文管理器,在执行过程离开with语句体时自动执行object.close(),一旦代码块运行完毕,它就会将事件关闭。
    • suppress:可以禁止任意数目的异常,如调用 suppress(FileNotFoundError)时,当文件不存在时不会抛出异常。
    • ExitStack:维护一个寄存器的栈,当退出with语句时,文件就会关闭,栈会按照相反的顺序调用这些上下文管理器。

    Python的with上下文管理器类似于go语言的defer,可以起到简化finally,方便处理异常的作用。

  • 相关阅读:
    mingW与cygwin
    Ruby on Rails 和 J2EE:两者能否共存?
    嵌入式Linux学习笔记(一) 启航、计划和内核模块初步体验
    嵌入式Linux学习笔记(六) 上位机QT界面实现和通讯实现
    嵌入式Linux问题总结(一) Ubuntu常用命令和编译问题解决方法
    嵌入式Linux学习笔记(五) 通讯协议制定和下位机代码实现
    嵌入式Linux学习笔记(四) 设备树和UART驱动开发
    嵌入式Linux学习笔记(三) 字符型设备驱动--LED的驱动开发
    嵌入式Linux学习笔记(二) 交叉编译环境和Linux系统编译、下载
    记录嵌入式面试的流程
  • 原文地址:https://www.cnblogs.com/FG123/p/9463680.html
Copyright © 2020-2023  润新知