python中的上下文管理器以及python内建模块contextlib的contextmanager方法
上下文管理器
上下文管理器是实现了上下文管理协议的对象,其特有的语法是“with …as”。主要用于保存和恢复各种全局状态,关闭文件等,并为try…except…finally提供了一个方便使用的封装。
上下文管理协议具体来说就是在类里面实现以下两个方法:
_enter_(): 从该方法进入运行时上下文,并返回当前对象或者与运行时上下文相关的其他对象。如果with语句有as关键词存在,返回值会绑定在as后的变量上。
_exit_(exc_type, exc_val, exc_tb): 退出运行时上下文,return True 如果 with 执行体有异常,则不会继续向上抛出异常;return Flase 如果 with 执行体有异常,则继续向上抛出异常。如果在执行with语句体时发生异常,那退出时参数会包括异常类型、异常值、异常追踪信息,否则,3个参数都是None。
下面,我们可以自己定义一个类来通过with进行上下文管理:
class MyContextManager:
def __enter__(self):
print("connect to contextmanager")
return self # return返回的可以是对象,会绑定给as后面的变量
def __exit__(self, exc_type, exc_val, exc_tb):
"""__exit__方法中:
1.如果return False:执行query_data方法有异常,则异常继续往上抛
2.如果return True:执行query_data方法有异常,则异常不会往上抛
"""
print('close the contextmanager')
# return False
return True
def query_data(self):
print('query data')
with MyContextManager() as m:
m.query_data()
执行以上代码,运行结果如下:

下面,我们在类的query_data方法中增加一个报错的a,当__exit__方法 return True 时,如下:
class MyContextManager:
def __enter__(self):
print("connect to contextmanager")
return self # return返回的可以是对象,会绑定给as后面的变量
def __exit__(self, exc_type, exc_val, exc_tb):
"""__exit__方法中:
1.如果return False:执行query_data方法有异常,则异常继续往上抛
2.如果return True:执行query_data方法有异常,则异常不会往上抛
"""
print('close the contextmanager')
# return False
return True
def query_data(self):
a
print('query data')
with MyContextManager() as m:
m.query_data()
运行结果如下:并不会执行 query_data() 方法
当__exit__方法 return False 时,如下:
class MyContextManager:
def __enter__(self):
print("connect to contextmanager")
return self # return返回的可以是对象,会绑定给as后面的变量
def __exit__(self, exc_type, exc_val, exc_tb):
"""__exit__方法中:
1.如果return False:执行query_data方法有异常,则异常继续往上抛
2.如果return True:执行query_data方法有异常,则异常不会往上抛
"""
print('close the contextmanager')
return False
# return True
def query_data(self):
a
print('query data')
with MyContextManager() as m:
m.query_data()
运行结果如下:会抛异常,

实际应用示例:
创建一个上下文管理器,这个上下文管理器将会创建一个SQLite数据库连接,当任务处理完毕,将会将其关闭。
import sqlite3 class DataConn:
def __init__(self,db_name):
self.db_name = db_name def __enter__(self):
self.conn = sqlite3.connect(self.db_name)
return self.conn def __exit__(self,exc_type,exc_val,exc_tb):
self.conn.close()
if exc_val:
raise if __name__ == "__main__":
db = "test/test.db"
with DataConn(db) as conn:
cursor = conn.cursor()
在上面的代码中,我们创建了一个类,获取到SQLite数据库文件的路径。__enter__方法将会自动执行,并返回数据库连接对象。现在我们已经获取到数据库连接对象,然后我们创建光标,向数据库写入数据或者对数据库进行查询。当我们退出with语句的时候,它将会调用__exit__方法用于执行和关闭这个连接。
Python的内建模块 contextlib
对于上下文的管理,python也提供了内建的模块contextlib来实现相同的机制,而且这种通过生成器和装饰器实现的上下文管理器,看起来比with语句和手动实现上下文管理协议更优雅。
from contextlib import contextmanager class MyContextManager:
def query_data(self):
# a
print('query data') @ contextmanager # 有了contextmanager我们就不需要手动实现enter和exit方法
def make_context_manager():
print('connect to contextmanager')
yield MyContextManager() # yield就相当于return,但是不会结束函数,而是暂时挂起,如果我们后续需要的话,继续调用这个函数,会从上次挂起的地方继续执行
print('close the contextmanager') with make_context_manager() as mc:
mc.query_data()
python中的上下文管理器以及python内建模块contextlib的contextmanager方法的更多相关文章
- (转)Python中的上下文管理器和Tornado对其的巧妙应用
原文:https://www.binss.me/blog/the-context-manager-of-python-and-the-applications-in-tornado/ 上下文是什么? ...
- Python中的上下文管理器和with语句
Python2.5之后引入了上下文管理器(context manager),算是Python的黑魔法之一,它用于规定某个对象的使用范围.本文是针对于该功能的思考总结. 为什么需要上下文管理器? 首先, ...
- 深入理解 Python 中的上下文管理器
提示:前面的内容较为基础,重点知识在后半段. with 这个关键字,对于每一学习Python的人,都不会陌生. 操作文本对象的时候,几乎所有的人都会让我们要用 with open ,这就是一个上下文管 ...
- python中实现上下文管理器的两种方法
上下文管理器: python中实现了__enter__和__exit__方法的对象就可以称之为上下文管理器 实现方法一举例: def File(object): def __init__(self, ...
- Python中的上下文管理器(contextlib模块)
上下文管理器的任务是:代码块执行前准备,代码块执行后收拾 1 如何使用上下文管理器: 打开一个文件,并写入"hello world" filename="my.txt&q ...
- python中利用上下文管理器来实现mysql数据库的封装
from pymysql import connect class DB(object): def __init__(self, password, database): # 1.连接数据库 self ...
- python中的上下文管理器
刚刚看了vamei大神的上下文管理器博客,理解如下: 其实我自己经常用到上下文管理器,尤其是在打开文件的时候,如果自己比较懒,不想手工打上f.close(),使用上下文管理器就ok拉. 上下文管理器就 ...
- Python - Context Manager 上下文管理器
什么是上下文管理器 官方解释... 上下文管理器是一个对象 它定义了在执行 with 语句时要建立的运行时上下文 上下文管理器处理进入和退出所需的运行时上下文以执行代码块 上下文管理器通常使用 wit ...
- Python深入02 上下文管理器
作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明.谢谢! 上下文管理器(context manager)是Python2.5开始支持的一种语 ...
- 【Python】【上下文管理器】
"""#[备注]#1⃣️try :仅当try块中没有异常抛出时才运行else块.#2⃣️for:仅当for循环运行完毕(即for循环没有被break语句终止)才运行els ...
随机推荐
- Kali Win-KeX SL
内容: 概述 先决条件 用法 开始 声音支持 多屏支持 停止 概述 无缝模式下的 Win-KeX 将在 Windows 桌面的屏幕顶部启动 Kali Linux 面板. 通过面板启动的应用程序将与 M ...
- [OpenCV实战]8 深度学习目标检测网络YOLOv3的训练
目录 1 数据集 1.1 下载openImages雪人数据[约1.5小时] 1.2 训练集测试集拆分 2 Darknet 2.1 下载并构建Darknet 2.2 修改代码以定期保存模型文件 2.3 ...
- Web初级——数组对象常用api
js数组常用api 连接函数:join("连接符") var array = [1,2,3,4,5] console.log(array.join("+")) ...
- IDEA 2022.1.3 配置 Tomcat 模板
本地运行 Tomcat 首先,下载得到 Tomcat 压缩包 选择合适的位置解压,路径不要有中文和空格 结构如下所示 目录结构说明: bin 可执行文件目录 conf 配置文件目录 lib 存放lib ...
- Linux音频采集和在国产化平台中遇到的坑(二)
Linux音频采集和在国产化平台中遇到的坑(二) ALSA采集这条路走不通,只能尝试其他途径,这里通过PulseAudio的接口成功实现了采集麦克风和系统声音的功能. linux PulseAudio ...
- vue学习笔记(一) ---- vue指令(总体大纲)
一.什么是Vue 官方文档:https://cn.vuejs.org/v2/guide/ 关键字: 渐进式框架 自底向上增量开发 视图层 单文件组件 复杂的单页应用 复杂的单页应用: 顾名思义,单页应 ...
- Python风格规范(转载)
Python风格规范(转载) https://zh-google-styleguide.readthedocs.io/en/latest/google-python-styleguide/python ...
- drf-视图集、路由系统、action装饰器
1.9个视图扩展类 1.两个视图基类:APIView.GenricAPIView 2.5个视图扩展类:CreateModelMixin,UpdateModelMixin,RetrieveModelMi ...
- .Net Core对于`RabbitMQ`封装分布式事件总线
首先我们需要了解到分布式事件总线是什么: 分布式事件总线是一种在分布式系统中提供事件通知.订阅和发布机制的技术.它允许多个组件或微服务之间的协作和通信,而无需直接耦合或了解彼此的实现细节.通过事件总线 ...
- springboot FilterRegistrationBean 拦截器的使用
1.创建一个filter package com.ruoyi.weixin.user.interator; import com.ruoyi.common.utils.SecurityUtils; i ...