python内置模块之上下文管理contextlib


Posted in Python onJune 14, 2022

Python中当我们们打开文本时,通常会是用with语句,with语句允许我们非常方便的使用资源,而不必担心资源没有关闭。

with open('/path/filename', 'r') as f:
    f.read()

然而,并不是只有open()函数返回fp对象才能使用 with 语句。实际上,任何对象,只要正确实现上下文管理,就可以使用with语句。

实现上下文管理是通过 __enter__ 和 __exit__ 这两个方法实现的。例如,下面的class实现了这两个方法:

class Query(object):
 
    def __init__(self, name):
        self.name = name
 
    def __enter__(self):
        print('Begin')
        return self
 
    def __exit__(self, exc_type, exc_value, traceback):
        if exc_type:
            print('Error')
        else:
            print('End')
 
    def query(self):
        print('Query info about %s...' % self.name)

这样我们可以把自己写的资源对象用于 with 语句。

with Query('Bob') as q:
    q.query()

一、@contextmanager

编写 __enter__ 和 __exit__ 仍然很繁琐,因此Python的标准库 contextlib 提供了更简单的写法,上面的代码可以改写为:

from contextlib import contextmanager
 
class Query(object):
 
    def __init__(self, name):
        self.name = name
 
    def query(self):
        print('Query info about %s...' % self.name)
 
@contextmanager
def create_query(name):
    print('Begin')
    q = Query(name)
    yield q
    print('End')

@contextmanager 这个装饰器接受一个 generator,用 yield 语句把 with ... as var 把变量输出去,然后,with 语句就可以正常的工作了:

with create_query('Bob') as q:
    q.query()

很多时候,我们希望在某段代码执行前后自动执行特定代码,也可以用 @contextmanager实现。

@contextmanager
def tag(name):
    print("<%s>" % name)
    yield
    print("" % name)
 
with tag("h1"):
    print("hello")
    print("world")

上述代码执行结果:

hello
world
</h1>

代码的执行顺序是:

  • with 语句 首先执行 yield 之前的语句,因此打印出.
  • yield 调用会执行 with 语句内部的所有语句,因此打印出 hello 和 world.
  • 最后执行yield之后的语句,打印出.

二、@closing

如果一个对象没有实现上下文,就不能使用 with 语句,但是可以用 closing() 来把对象变为上下文对象。

from contextlib import closing
from urllib.request import urlopen
 
with closing(urlopen('https://www.python.org')) as page:
    for line in page:
        print(line)

closing 也是一个经过 @contextmanager 装饰的generator

@contextmanager
def closing(thing):
    try:
        yield thing
    finally:
        thing.close()

它的作用就是把任意对象变为上下文对象,并支持 with语句。

到此这篇关于python内置模块之上下文管理contextlib的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
简单的Python的curses库使用教程
Apr 11 Python
利用Python中的输入和输出功能进行读取和写入的教程
Apr 14 Python
Python输出汉字字库及将文字转换为图片的方法
Jun 04 Python
Python实现脚本锁功能(同时只能执行一个脚本)
May 10 Python
使用Python爬取最好大学网大学排名
Feb 24 Python
pandas apply 函数 实现多进程的示例讲解
Apr 20 Python
pandas把所有大于0的数设置为1的方法
Jan 26 Python
python3实现表白神器
Apr 09 Python
python自动化测试之DDT数据驱动的实现代码
Jul 23 Python
Python中six模块基础用法
Dec 08 Python
python3.6.5基于kerberos认证的hive和hdfs连接调用方式
Jun 06 Python
Python 无限级分类树状结构生成算法的实现
Jan 21 Python
Python时间操作之pytz模块使用详解
Django框架之路由用法
Jun 10 #Python
深入理解pytorch库的dockerfile
Jun 10 #Python
如何利用python实现列表嵌套字典取值
Jun 10 #Python
python中filter,map,reduce的作用
Jun 10 #Python
Django框架中模型的用法
Jun 10 #Python
Django框架中视图的用法
Jun 10 #Python
You might like
php imagecreatetruecolor 创建高清和透明图片代码小结
2010/05/15 PHP
php数据结构 算法(PHP描述) 简单选择排序 simple selection sort
2011/08/09 PHP
PHP中几个常用的魔术常量
2012/02/23 PHP
如何利用预加载优化Laravel Model查询详解
2017/08/11 PHP
JavaScript实用技巧(一)
2010/08/16 Javascript
js实现的仿新浪微博完美的时间组件升级版
2011/12/20 Javascript
JQuery radio(单选按钮)操作方法汇总
2015/04/15 Javascript
关于Sequelize连接查询时inlude中model和association的区别详解
2017/02/27 Javascript
jquery图片放大镜效果
2017/06/23 jQuery
最新Javascript程序员面试试题和解题方法
2017/11/23 Javascript
React Native自定义控件底部抽屉菜单的示例
2018/02/08 Javascript
详解如何快速配置webpack多入口脚手架
2018/12/28 Javascript
vue-cli webpack配置文件分析
2019/05/20 Javascript
JavaScript实现省份城市的三级联动
2020/02/11 Javascript
简单介绍Ruby中的CGI编程
2015/04/10 Python
Django项目开发中cookies和session的常用操作分析
2018/07/03 Python
Python3获取电脑IP、主机名、Mac地址的方法示例
2019/04/11 Python
python面试题之列表声明实例分析
2019/07/08 Python
浅谈在django中使用filter()(即对QuerySet操作)时踩的坑
2020/03/31 Python
Python实现进度条和时间预估的示例代码
2020/06/02 Python
Django Form常用功能及代码示例
2020/10/13 Python
Python Process创建进程的2种方法详解
2021/01/25 Python
CSS3制作炫酷的自定义发光文字
2016/03/28 HTML / CSS
【HTML5】Canvas绘制简单图片教程
2016/05/13 HTML / CSS
美国女鞋品牌:naturalizer(娜然)
2016/08/01 全球购物
马来西亚最好的婴儿商店:Motherhood
2017/09/14 全球购物
校本教研工作制度
2014/01/22 职场文书
创业者是否需要商业计划书?
2014/02/07 职场文书
趣味运动会活动方案
2014/02/12 职场文书
购房协议书
2014/04/11 职场文书
北京导游词
2015/02/12 职场文书
写给老婆的保证书
2015/02/27 职场文书
社团个人总结范文
2015/03/05 职场文书
工伤事故赔偿协议书
2015/08/06 职场文书
五年级作文之想象作文
2019/10/30 职场文书
Pycharm连接远程服务器并远程调试的全过程
2021/06/24 Python