详解Python多线程下的list


Posted in Python onJuly 03, 2020

list 是 Python 常用的几个基本数据类型之一.正常情况下我们会对 list 有增删改查的操作,显然易见不会有任何问题.那么如果我们试着在多线程下操作list 会有问题吗?

多线程下的 list

安全 or 不安全? 不安全!

通常我们说的线程安全是指针对某个数据结构的所有操作都是线程安全,在这种定义下,Python 常用的数据结构 list,dict,str 等都是线程不安全的

尽管多线程下的 list 是线程不安全的,但是在 append 的操作下是它又是线程安全的.

如何判断线程安全呢?

对于线程安全不安全,我们可以通过极端条件下去复现,从而得出结论。比如说判断 list 是否线程安全

import threading
import time

# 随意设置 count 的值,值越大错误抛出的越快
count = 1000
l = []

def add():
  for i in range(count):
    l.append(i)
    time.sleep(0.0001)

def remove():

  for i in range(count):
    l.remove(i)
    time.sleep(0.0001)


t1 = threading.Thread(target=add)
t2 = threading.Thread(target=remove)
t1.start()
t2.start()
t1.join()
t2.join()
print(l)

有时候一次运行并不一定就会出错,多次重试之后会出现类似下面的错误

详解Python多线程下的list

很显然这种操作方式不具有普适性,如果要是欧气太强,说不定会一直不出现异常。

那么出了这种方式,有没有比较简单有效的方法吗?答案是有的

dis

dis 库是 Python 自带的一个库,可以用来分析字节码。这里我们需要有这样的认识,字节码的每一行都是一个原子操作,多线程切换就是以原子操作为单位的,如果一个操作需要两行字节码就说明它是线程不安全的

remove

这里我们先看一下上面 listremove 操作

>>> import dis
>>> def test_remove():
...   a = [1]
...   a.remove(0)
... 
>>> dis.dis(test_remove)
 2      0 LOAD_CONST        1 (1)
       2 BUILD_LIST        1
       4 STORE_FAST        0 (a)

 3      6 LOAD_FAST        0 (a)
       8 LOAD_ATTR        0 (remove)
       10 LOAD_CONST        2 (0)
       12 CALL_FUNCTION      1
       14 POP_TOP
       16 LOAD_CONST        0 (None)
       18 RETURN_VALUE

从上面不难看出,整个 remove 操作被分成了好几条指令,这就意味着在多线程情况下会出现错乱的情况,试想一下,如果多线程下都去 remove 列表的话,并且不按照顺序,很容易出现问题。

append

在最上面我们说到,list append 操作是线程安全的,那么究竟是为什么呢?我们同样来用 dis 查看一下

8     19 LOAD_GLOBAL       0 (a)
      22 LOAD_ATTR        2 (append)
      25 LOAD_CONST        2 (1)
      28 CALL_FUNCTION      1
      31 POP_TOP

这里显然,append 也是有几条指令,势必在多线程执行的情况下也会发生交错,但是对于多线程下我们操作 append, 我们肯定也不会在乎这个时候 list 到顺序问题了,所以我们说它的 append 是线程安全的

参考

https://stackoverflow.com/questions/6319207/are-lists-thread-safe/19728536#19728536

https://docs.python.org/3/faq/library.html#what-kinds-of-global-value-mutation-are-thread-safe

以上就是详解Python多线程下的list的详细内容,更多关于Python多线程下的list的资料请关注三水点靠木其它相关文章!

Python 相关文章推荐
python生成随机图形验证码详解
Nov 08 Python
运用TensorFlow进行简单实现线性回归、梯度下降示例
Mar 05 Python
使用pandas对两个dataframe进行join的实例
Jun 08 Python
python3 打开外部程序及关闭的示例
Nov 06 Python
手把手教你使用Python创建微信机器人
Apr 29 Python
Python何时应该使用Lambda函数
Jul 02 Python
python网络爬虫 Scrapy中selenium用法详解
Sep 28 Python
matlab中imadjust函数的作用及应用举例
Feb 27 Python
使用python将微信image下.dat文件解密为.png的方法
Nov 30 Python
opencv python 对指针仪表读数识别的两种方式
Jan 14 Python
手把手教你配置JupyterLab 环境的实现
Feb 02 Python
解决pytorch 的state_dict()拷贝问题
Mar 03 Python
Python 字符串池化的前提
Jul 03 #Python
Pycharm打开已有项目配置python环境的方法
Jul 03 #Python
使用Dajngo 通过代码添加xadmin用户和权限(组)
Jul 03 #Python
windows支持哪个版本的python
Jul 03 #Python
Django Form设置文本框为readonly操作
Jul 03 #Python
完美解决TensorFlow和Keras大数据量内存溢出的问题
Jul 03 #Python
Keras 在fit_generator训练方式中加入图像random_crop操作
Jul 03 #Python
You might like
php设计模式 Mediator (中介者模式)
2011/06/26 PHP
php随机生成数字字母组合的方法
2015/03/18 PHP
php实现的通用图片处理类
2015/03/24 PHP
joomla实现注册用户添加新字段的方法
2016/05/05 PHP
js Form.elements[i]的使用实例
2011/11/13 Javascript
利用div+jquery自定义滚动条样式的2种方法
2013/07/18 Javascript
jQuery焦点图切换特效插件封装实例
2013/08/18 Javascript
js判断选择时间不能小于当前时间的示例代码
2013/09/24 Javascript
java和javascript获取word文档的书签位置对比
2014/06/19 Javascript
浅析js预加载/延迟加载
2014/09/25 Javascript
JavaScript实现节点的删除与序号重建实例
2015/08/05 Javascript
分享我的jquery实现下拉菜单心的
2015/11/29 Javascript
vue.js绑定class和style样式(6)
2016/12/09 Javascript
bootstrap fileinput组件整合Springmvc上传图片到本地磁盘
2017/05/11 Javascript
深入讲解xhr(XMLHttpRequest)/jsonp请求之abort
2017/07/26 Javascript
Vue 2.5.2下axios + express 本地请求404的解决方法
2018/02/21 Javascript
vue使用iframe嵌入网页的示例代码
2020/06/09 Javascript
vue v-for循环重复数据无法添加问题解决方法【加track-by='索引'】
2019/03/15 Javascript
Vue 动态添加路由及生成菜单的方法示例
2019/06/20 Javascript
vue v-for直接循环数字实例
2019/11/07 Javascript
基于vue3.0.1beta搭建仿京东的电商H5项目
2020/05/06 Javascript
Python中的Numpy入门教程
2014/04/26 Python
Python数组条件过滤filter函数使用示例
2014/07/22 Python
python删除特定文件的方法
2015/07/30 Python
Python每天必学之bytes字节
2016/01/28 Python
用Python实现随机森林算法的示例
2017/08/24 Python
详解Python3注释知识点
2019/02/19 Python
基于python实现微信好友数据分析(简单)
2020/02/16 Python
AmazeUI 手机版页面的顶部导航条Header与侧边导航栏offCanvas的示例代码
2020/08/19 HTML / CSS
销售副总经理岗位职责
2013/12/11 职场文书
我未来的职业规划范文
2014/01/11 职场文书
让世界充满爱演讲稿
2014/05/24 职场文书
铅球加油稿100字
2014/09/26 职场文书
2014年科普工作总结
2014/12/06 职场文书
2015年小学图书室工作总结
2015/05/18 职场文书
高考1977观后感
2015/06/04 职场文书