Python上下文管理器全实例详解

yipeiwu_com6年前Python基础

Python上下文管理器

简介

最近用到这个,仔细了解了一下,感觉是十分有用的,记录一下

使用场景

当我们需要获取一个临时打开的资源,并在使用完毕后进行资源释放和异常处理,利用try-catch语句可以完成,举个例子。

打开文件:

f = None
try:
 print("try")
 f = open("__init__.py", "r")
 print(f.read())
except Exception as e:
 print("exception")
finally:
 if f:
  print("finally")
  f.close()

利用上下文管理器:

class OpenHandle:

 def __init__(self, filename, mode):
  self.filename = filename
  self.mode = mode

 def __enter__(self):
  self.f = open(self.filename, self.mode)
  return self.f

 def __exit__(self, exc_type, exc_val, exc_tb):
  if exc_type:
   print("exception")
  else:
   print("normal")
  self.f.close()

with OpenHandle("book.txt", "r") as f:
 print(f.read())

这样可以利用with-as语句改写代码,让程序员关注业务主流程,去掉对于资源的获取和关闭这些重复操作。提升代码的可读性。好处很大。

执行顺序

执行顺序是理解这种写法的关键:

  • 初始化,执行handle的__init__()
  • __enter__()方法,获取资源对象,返回给as后的变量
  • 业务代码逻辑
  • __exit__方法,传入3个参数,异常类型,异常对象,调用栈对象,无异常都为None
  • 抛出异常或者正常结束

函数式上下文管理器

利用from contextlib import contextmanager这个装饰器可以将函数装饰为上下文管理器,其实这个装饰背后也是返回一个实现了__enter__和__exit__方法的类

from contextlib import contextmanager

@contextmanager
def managed_resource(*args, **kwds):
 # Code to acquire resource, e.g.:
 resource = acquire_resource(*args, **kwds)
 try:
  yield resource
 finally:
  # Code to release resource, e.g.:
  release_resource(resource)

>>> with managed_resource(timeout=3600) as resource:
...  # Resource is released at the end of this block,
...  # even if code in the block raises an exception

模板代码

sqlalchemy会话上下文管理器

利用这个管理sqlalchemy会话对象的获取和释放,控制事务是再合适不过了

class DbTransaction:

 def __init__(self, session_maker):
  self.session_maker = session_maker

 def __enter__(self):
  self.session = self.session_maker()
  return self.session

 def __exit__(self, exc_type, exc_val, exc_tb):
  if exc_type:
   self.session.rollback()
  else:
   self.session.commit()
  self.session.close()
  return False if exc_type else True

以上就是全部相关知识点,感谢大家的学习和对【听图阁-专注于Python设计】的支持。

相关文章

用python写一个windows下的定时关机脚本(推荐)

由于本人经常使用笔记本共享WiFi,但是又不想笔记本开机一夜(为了低碳环保嘛 ~_~!),所以每次都要用使用DOS命令关机,感觉好麻烦。正好最近在学习Python,于是决定用python...

Python数据持久化存储实现方法分析

本文实例讲述了Python数据持久化存储实现方法。分享给大家供大家参考,具体如下: 1、pymongo的使用 前三步为创建对象 第一步创建连接对象 conn = pymong...

python中的&&及||的实现示例

首先说明一下,在python中是没有&&及||这两个运算符的,取而代之的是英文and和or。其他运算符没有变动。 接着重点要说明的是python中的a.any(),我之所以会涉及到这个函...

Python流程控制 if else实现解析

Python流程控制 if else实现解析

一、流程控制 假如把程序比做走路,那我们到现在为止,一直走的都是直路,还没遇到过分岔口。当遇到分岔口时,你得判断哪条岔路是你要走的路,如果我们想让程序也能处理这样的判断,该怎么办?很简...

利用pandas将非数值数据转换成数值的方式

利用pandas将非数值数据转换成数值的方式

handle non numerical data 举个例子,将性别属性男女转换成0-1,精通ML的小老弟们可以略过本文~~, 这里不考虑稀疏向量的使用,仅提供一些思路。本来想直接利用p...