python上下文管理,with语句
今天在网上看到一段代码,其中使用了with seam:初见不解其意,遂查询资料.
代码:
#! /usr/bin/env python
# -*- coding:utf-8 -*-
import time
from random import random
from threading import Thread,Semaphore sema = Semaphore(3) def foo(tid):
with sema:
print("{} acquire sema".format(tid))
wt = random() * 2
time.sleep(wt)
print("{} release sema".format(tid)) threads = [] for i in range(5):
t = Thread(target=foo,args=(i,))
threads.append(t)
t.start() for t in threads:
t.join()
查询 python核心编程第二版,其中有个章节,专门介绍了with语句和上下文管理.
with语句,在Python2.6正式启用,和try-except-finally 类似,with语句也是用来简化代码的.Python中,并非任意符号都可以使用with语句,with语句仅仅工作于支持上下文管理协议的对象.
with应用场景:打开文件,日志,数据库,线程资源,简单同步,数据库连接等等.
with context_expr [as var]: ##context_expr:上下文表达式,[]可选
with_suite
能和with一起使用的成员列表:
file
decimal.Context
thread.LockType
threading.Lock
threading.RLock
threading.Condition
threading.Semaphore
threading.BoundedSemaphore
最最常见的with用法:
with open("file","r") as f:
for line in f:
pass
上面的代码都做了什么操作?
程序试图打开一个文本,如果一切正常,把文本对象赋值给f,然后用迭代器遍历文本中的每一行.当完成时,关闭文本.
无论在这段代码的开始,中间,还是结束时发生了异常,都会执行清理的代码,此外文件仍然被会自动的关闭.
先上一个最简单的代码:
class Context:
def __init__(self,name):
self.name = name
def __enter__(self):
print("Begin.__enter__")
return self
def __exit__(self, exc_type, exc_val, exc_tb):
print("End.__exit__")
def context(self):
print("This is context ...{}".format(self.name)) with Context("xurui") as context: ##如果带上 as 变量,那么__enter__()方法必须得返回一个东西,要不然会报错..
context.context()
with Context("xurui"):
Context("xurui").context()
演示代码:
class Sample:
"""
##执行__enter__方法,它将完成with语句块执行前的所有准备工作,如果with xx 后面带上参数,as val,那么__enter__返回值将赋值给
val,否则,丢弃返回值"""
def __enter__(self):
print("In __enter__()")
return "Foo" ##返回"Foo"给as Sample中的Sample
def __exit__(self, exc_type, exc_val, exc_tb):
print("In __exit__()") def get_sample():
print(type(Sample()))
return Sample() with get_sample() as Sample:
print("sample:{}".format(Sample)) 结果:
In __enter__()
sample:Foo
In __exit__()
但这都不是with的牛逼功能,with最强的地方,还是用来处理异常...
__exit__(),有三个参数,类型(异常类),值(异常实例),和回溯(回溯对象).
演示代码:
class Sample:
"""
##执行__enter__方法,它将完成with语句块执行前的所有准备工作,如果with xx 后面带上参数,as val,那么__enter__返回值将赋值给
val,否则,丢弃返回值"""
def __enter__(self):
return self
def __exit__(self, exc_type, exc_val, exc_tb):
print("type:{},\nvalue:{},\ntrace:{}".format(exc_type,exc_val,exc_tb)) def do_something(self):
bar = 1 / 0
return bar + 10 with Sample() as Sample:
Sample.do_something()
print("sample:{}".format(Sample)) 结果:
type:<class 'ZeroDivisionError'>,
value:division by zero,
trace:<traceback object at 0x0000000001074CC8>
Traceback (most recent call last):
File "C:/Users/xurui/PycharmProjects/q1/2017-03-01/error.py", line 55, in <module>
Sample.do_something()
File "C:/Users/xurui/PycharmProjects/q1/2017-03-01/error.py", line 51, in do_something
bar = 1 / 0
ZeroDivisionError: division by zero
import queue
import contextlib @contextlib.contextmanager
def worker_state(xxx, val):
xxx.append(val)
# print(xxx)
try:
yield
finally:
xxx.remove(val)
# print(xxx) q = queue.Queue()
li = []
q.put("xurui")
with worker_state(li, 1):
print("before", li)
q.get()
print("after", li)
自定义一个open文件
import contextlib @contextlib.contextmanager
def MyOpen(filename, mode):
try:
f = open(filename, mode, encoding='utf')
except Exception as e:
pass
else:
yield f ##f return 给 as f的f
finally:
f.close() with MyOpen("1.py", 'r') as f:
ret = f.readlines()
print(ret)
python上下文管理,with语句的更多相关文章
- python上下文管理
一.python上下文介绍: python中的上下文,指的就是代码所执行的环境状态,或者运行的场景 python上下文管理器规定了某个对象的使用范围,当进入或者离开了使用范围,会有相应的操作,多用于资 ...
- python上下文管理器ContextLib及with语句
http://blog.csdn.net/pipisorry/article/details/50444736 with语句 with语句是从 Python 2.5 开始引入的一种与异常处理相关的功能 ...
- python上下文管理器及with语句
with语句支持在一个叫上下文管理器的对象的控制下执行一系列语句,语法大概如下: with context as var: statements 其中的context必须是个上下文管理器,它实现了两个 ...
- python 上下文管理器
作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明.谢谢! 上下文管理器(context manager)是Python2.5开始支持的一种语 ...
- Python 上下文管理器和else块
最终,上下文管理器可能几乎与子程序(subroutine)本身一样重要.目前,我们只了解了上下文管理器的皮毛--Basic 语言有with 语句,而且很多语言都有.但是,在各种语言中 with 语句的 ...
- Python上下文管理器
在Python中让自己创建的函数.类.对象支持with语句,就实现了上线文管理协议.我们经常使用with open(file, "a+") as f:这样的语句,无需手动调用f.c ...
- Python上下文管理器 with
对于系统资源的操作,如:文件操作.数据库操作等,我们往往打开文件.连接数据库后忘了将其close掉,这时就可能会引发异常,因此我们常用的做法是: # coding:utf-8 f = open(&qu ...
- Python上下文管理协议:__enter__和__exit__
上下文管理器(context manager)是Python2.5开始支持的一种语法,用于规定某个对象的使用范围.一旦进入或者离开该使用范围,会有特殊操作被调用 (比如为对象分配或者释放内存).它的语 ...
- Python上下文管理器(Context managers)
上下文管理器(Context managers) 上下文管理器允许你在有需要的时候,精确地分配和释放资源. 使用上下文管理器最广泛的案例就是with语句了.想象下你有两个需要结对执行的相关操作,然后还 ...
随机推荐
- hdu 2586 How far away ? ( 离线 LCA , tarjan )
How far away ? Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)To ...
- RocksDB Rate Limiter源码解析
这次的项目我们重点关注RocksDB中的一个环节:Rate Limiter.其实Rate Limiter的思想在很多其他系统中也很常用. 在RocksDB中,后台会实时运行compaction和flu ...
- 微信小程序css篇----flex模型
一.Flex布局是什么? Flex是Flexible Box的缩写,意为"弹性布局",用来为盒状模型提供最大的灵活性. 任何一个容器都可以指定为Flex布局. .box{displ ...
- Codeforces Round #426 (Div. 2) - D
题目链接:http://codeforces.com/contest/834/problem/D 题意:给定一个长度为n的序列和一个k,现在让你把这个序列分成刚好k段,并且k段的贡献之和最大.对于每一 ...
- 009-流程控制 for 语句
流程控制 for 语句 ##################### 语法一 ################################# #!/bin/bash do echo $i done ...
- mock.js模拟ajax数据请求
在我们开发过程中存在着前端页面ui完成了,但是没有接口进行联调数据的情况,现在介绍一下用mock.js来完成数据的请求.这样在后期我们的后台接口完成后只需要更改请求的接口名字即可!前提是你的模拟字段名 ...
- MySQL常见的三种存储引擎
原文链接:https://www.cnblogs.com/yuxiuyan/p/6511837.html 简单来说,存储引擎就是指表的类型以及表在计算机上的存储方式. 存储引擎的概念是MySQL的特点 ...
- vue-cli项目中引入全局scss
加载一个全局设置文件 在每个组件里加载一个设置文件,而无需每次都将其显式导入,是一个常见的需求.比如为所有组件全局使用 scss 变量.为了达成此目的: npm install sass-resour ...
- 推荐一些CSS命名规范
常用的CSS命名规则 头:header内容:content/container尾:footer导航:nav侧栏:sidebar栏目:column页面外围控制整体佈局宽度:wrapper左右中:left ...
- proxy配置
关于config.js里面proxy的配置: proxy: { '/api': { target: 'http://192.168.***.**:8500', cha ...