zoukankan      html  css  js  c++  java
  • [Coding笔记] Python上下文管理协议

    在python中,支持了上下文管理协议的对象可以使用在with ... as ...语句中,如:

    with open("a.txt") as file_pipline:
        ...
    

    为了让一个对象兼容 with 语句,我们需要实现__enter__()__exit__() 方法。 例如,我们可以这样实现一个建立网络连接的类:

    from socket import socket, AF_INET, SOCK_STREAM
    
    class LazyConnection:
        def __init__(self, address, family=AF_INET, type=SOCK_STREAM):
            self.address = address
            self.family = family
            self.type = type
            self.sock = None
    
        def __enter__(self):
            if self.sock is not None:
                raise RuntimeError('Already connected')
            self.sock = socket(self.family, self.type)
            self.sock.connect(self.address)
            return self.sock
    
        def __exit__(self, exc_ty, exc_val, tb):
            self.sock.close()
            self.sock = None
    

    当出现 with 语句的时候,对象的 __enter__() 方法被触发, 它返回的值(如果有的话)会被赋值给 as 声明的变量。然后,with 语句块里面的代码开始执行。 最后,__exit__() 方法被触发进行清理工作。

    不管 with 代码块中发生什么,上面的控制流都会执行完,就算代码块中发生了异常也是一样的。 事实上,__exit__() 方法的第三个参数包含了异常类型、异常值和追溯信息(如果有的话)。 __exit__() 方法能自己决定怎样利用这个异常信息,或者忽略它并返回一个None值。 如果 __exit__() 返回 True ,那么异常会被清空,就好像什么都没发生一样, with 语句后面的程序继续在正常执行。


    在项目实践中的代码实例:

    class SSHConnector:
        def __init__(self, ip):
            self.ip = ip
            ...
    
        def __enter__(self):
            ssh = paramiko.SSHClient()
            ...
            self.ssh = ssh
            return ControlInstance(ssh)
    
        def __exit__(self, exc_type, exc_val, exc_tb):
            self.ssh.close()
            if exc_type:
                # 错误类型,错误值,错误追溯信息,无错误时默认为None
                print(exc_type, exc_val, exc_tb)
    
    class ControlInstance:
        def __init__(self, ssh):
            self.ssh = ssh
    
        def execute(self, command):
            stdin, stdout, stderr = self.ssh.exec_command(command)
            result = bytes.decode(stdout.read())
            return result
    

    这段代码用来创建一个SSH连接,在类中通过实现上下文管理协议使其支持with语句。

    参考:让对象支持上下文管理协议

  • 相关阅读:
    打包CAB大全
    设置VC6为默认异常调试工具
    XP系统遍历所有进程
    编写有界面的系统服务程序
    GOOGLE C++编程规范
    编写有界面的系统服务程序
    VC下音频文件的播放
    用MFC建立COM服务器对象的框架步骤
    注册OCX失败:由于应用程序配置不正确,程序未能启动.重新安装应用程序可能会纠正这个错误
    MediaPlayer属性大全
  • 原文地址:https://www.cnblogs.com/lokvahkoor/p/11934876.html
Copyright © 2011-2022 走看看