threading.local和高级
threading.local特点
①为每个线程开辟空间,让你进行存取值(根据线程ID来固定某个值)
②flask中没有threading.local,但是flask中的上下文管理的思想是借鉴的threading.local.
③在线程关闭之前值保持不变,线程关闭后值就清空了.
普通多线程
import time
import threading class Foo(object):
def __init__(self):
self.num = 0 val2 = Foo() def task(i):
val2.num = i
time.sleep(1)
print(val2.num) for i in range(4):
t = threading.Thread(target=task,args=(i,))
t.start() 结果:
3
3
3
3
4个值全一样
threading.local多线程
import time
import threading
# 当每个线程在执行 val1.xx=1 ,在内部会为此线程开辟一个空间,来存储 xx=1
# val1.xx,找到此线程自己的内存地址去取自己存储 xx
val1 = threading.local() def task(i):
val1.num = i
time.sleep(1)
print(val1.num) for i in range(4):
t = threading.Thread(target=task,args=(i,))
t.start 输出结果:
0
1
2
3
四个结果不同
自定义threading.local
import threading
"""
storage = { #自定义的维护一个这样的字典
1111:{'x1':0},
1112:{'x1':1}
1113:{'x1':2}
1114:{'x1':3}
1115:{'x1':4}
}
"""
class Local(object):
def __init__(self):
object.__setattr__(self,'storage',{}) def __setattr__(self, key, value):
ident = threading.get_ident() #这个就是线程id
if ident in self.storage:
self.storage[ident][key] = value
else:
self.storage[ident] = {key:value} def __getattr__(self, item):
ident = threading.get_ident() #这个就是线程id
if ident not in self.storage:
return
return self.storage[ident].get(item) local = Local() def task(arg):
local.x1 = arg
print(local.x1) for i in range(5):
t = threading.Thread(target=task,args=(i,))
t.start() 输出:
0
1
2
3
4
会根据你不同的线程ID来输出不同的值
加强版自定义threading.local
flask的上下文管理就这样
原来维护的是一个字典里面还是字典:
"""
storage = {
1111:{'x1':0},
1112:{'x1':1}
1113:{'x1':2}
1114:{'x1':3}
1115:{'x1':4}
}
"""
加强版维护的是一个字典里面是字典加列表:
"""
storage = {
1111:{'x1':[0,1]},
1112:{'x1':[0,1,2]}
1113:{'x1':[0,1,3]}
1114:{'x1':[0,1,5]}
1115:{'x1':[0,1,6]}
}
"""
这个维护的列表要当做栈(append往里加,如果是取值就用[-1],要是拿走值就用pop)来使用,后进先出 import threading
"""
storage = {
1111:{'x1':[]},
1112:{'x1':[]}
1113:{'x1':[]}
1114:{'x1':[]}
1115:{'x1':[]},
1116:{'x1':[]}
}
"""
class Local(object):
def __init__(self):
object.__setattr__(self,'storage',{}) def __setattr__(self, key, value):
ident = threading.get_ident()
if ident in self.storage:
self.storage[ident][key].append(value)
else:
self.storage[ident] = {key:[value,]} def __getattr__(self, item):
ident = threading.get_ident()
if ident not in self.storage:
return
return self.storage[ident][item][-1] local = Local() def task(arg):
local.x1 = arg
print(local.x1) for i in range(5):
t = threading.Thread(target=task,args=(i,))
t.start()
输出:
0
1
2
3
4
threading.local和高级的更多相关文章
- 03 flask源码剖析之threading.local和高级
03 threading.local和高级 目录 03 threading.local和高级 1.python之threading.local 2. 线程唯一标识 3. 自定义threading.lo ...
- flask 源码专题(七):threading.local和高级
1.python之threading.local 当每个线程在执行 val.num=1 ,在内部会为此线程开辟一个空间,来存储 num=1 val.num,找到此线程自己的内存地址去取自己存储 num ...
- 自定义threading.local
1.threading相关. # Author:Jesi # Time : 2018/12/28 14:21 import threading import time from threading i ...
- threading.local学习
多线程抢占问题 import time import threading obj = 5 def task(arg): global obj obj = arg time.sleep(1) print ...
- Threading.local
在多线程环境下,每个线程都有自己的数据.一个线程使用自己的局部变量比使用全局变量好,因为局部变量只有线程自己能看见,不会影响其他线程,而全局变量的修改必须加锁. Threading.local可以创建 ...
- 网络编程 多线程/socketserver模块/ threading.local
线程:进程中负责程序执行的执行单元. 多线程:在1个进程中存在多个线程. 进程只是用来把资源集中在一起,而线程才是cpu上的执行单位. 每个进程都会默认有一个控制线程也叫作主线程. 进程之间是竞争关系 ...
- 多线程局部变量之threading.local()用法
假如,开了十个线程并且做同样的一件事,他们需要带着自己的数据进来,完成事情后带着自己的数据出去.如果是并发,同时进来,他们的数据就会混乱. 一般情况,我们加锁就可以了,一个人先进来,先加锁,另一个人过 ...
- python之threading.local
简述: threading.local是全局变量但是它的值却在当前调用它的线程当中 作用: 在threading module中,有一个非常特别的类local.一旦在主线程实例化了一个local,它会 ...
- [Python 多线程] threading.local类 (六)
在使用threading.local()之前,先了解一下局部变量和全局变量. 局部变量: import threading import time def worker(): x = 0 for i ...
随机推荐
- ES5新增的数组方法
ES5新增:(IE9级以上支持)1.forEach():遍历数组,无返回值,不改变原数组.2.map():遍历数组,返回一个新数组,不改变原数组.3.filter():过滤掉数组中不满足条件的值,返回 ...
- luogu P3975 [TJOI2015]弦论 SAM
luogu P3975 [TJOI2015]弦论 链接 bzoj 思路 建出sam. 子串算多个的,统计preant tree的子树大小,否则就是大小为1 然后再统计sam的节点能走到多少串. 然后就 ...
- luoguP1742 最小圆覆盖
最小圆覆盖 首先 没错,我是个蒟蒻.luogu 流程 圆 C; for(i=1 to n) { if(P[i] 不在 C 内) { C = {P[i], 0}; for(j=1 to i-1) { i ...
- yum本地安装rrdtool报错,提示版本冲突的解决办法
[root@mysql-mon40 mm]# yum localinstall rrdtool-1.4.7-1.el6.rfx.x86_64.rpm -y 错误: Multilib version p ...
- nagios监控的安装
本文中,物理机IP 192.168.1.105虚拟linux主机ip 192.168.1.10安装apache和phpApache 和Php 不是安装nagios 所必须的,但是nagios提供了we ...
- 小程序支持原生async方法
下载最新版本的微信开发工具,社区链接https://developers.weixin.qq.com/community/develop/doc/00066877c54eb0ff5488b54885b ...
- FZU Monthly-201909 获奖名单
FZU Monthly-201909 获奖名单 冠军: 空缺 一等奖: 张咏真 S031802540 孔铖晗 S031802115 二等奖: 苏锦程 S031802325 林柄灿 S031802117 ...
- 面试突击(七)——JVM如何加载Java字节码信息的?
声明:本文图片均来自网络,我只是进行了选择,利用一图胜千言的力量来帮助自己快速的回忆相关的知识点 1:先看一下Java类文件的转换过程,如下所示,Java字节码文件是通过类加载子系统来放入JVM的内存 ...
- mybatis如何接受map类型的参数
Mybatis传入参数类型为Map mybatis更新sql语句: ? 1 2 3 4 5 6 7 8 9 <update id="publishT00_notice" ...
- 远程控制分析之VBS编码转换
简介 分析这种VBS简单chr()函数编码的脚本技巧.只需要把vbs的execute()函数换成信息输出到控制台(dos窗口)函数就可以了. WSH.Echo "print your mes ...