python threading2种调用方式实例
1.认识GIL:
说到GIL一直是代码专家们一直以来想要解决的问题,也是被许多程序员诟病的,下面带领大家看下官方threading模块document中如何去描述对于GIL这个全局解释器锁的:https://docs.python.org/3/library/threading.html
全局解释器锁
所使用的机制的CPython解释器来确保只有一个线程执行的Python 字节码在一个时间。通过使对象模型(包括关键的内置类型,例如dict
)隐式安全地防止并发访问,从而简化了CPython的实现。锁定整个解释器可以使解释器更容易进行多线程处理,但会牺牲多处理器机器提供的许多并行性。
但是,某些扩展模块(标准的或第三方的)被设计为在执行诸如压缩或散列之类的计算密集型任务时释放GIL。另外,在执行I / O时,始终释放GIL。
过去创建“自由线程”解释器(一种以更精细的粒度锁定共享数据的解释器)的努力并未成功,因为在常见的单处理器情况下性能会受到影响。相信克服该性能问题将使实施更加复杂,因此维护成本更高。
在这里专门对全局解释器锁的概念引入时说了这么一段话,第一指明了GIL造成了python解释器一次只有一个线程可以获取解释器锁,也就是解释器本身是自带锁的,谁先拿到谁就可以抢占到cpu的资源,
从而导致了python无论一个线程怎么去跑,都只能最多跑满一个cpu核心,就造成了多核cpu资源的无法利用的带来的资源浪费,但是这是否就意味着python一无是处呢,答案肯定No!,虽然GIL对于cpu密集的支持
不是那么的友好,但是,对于IO密集的支持恰恰是其他语言所无法比拟的,就拿asyncio这这个协程库来讲:https://docs.python.org/3/library/asyncio.html
1.第一部分认识多线程创建以及调用,上一节我讲解了源码关于多线程实现方式有两种:第一种通过Thread类传入可调用target对象,第二种继承Thread类并重写run方法:
下面就以target进行举例:
可以看到线程的资源抢占效果;证明GIL锁的的确真实存在的;
先在我们如果更换t.join()到t1.start()的后面会发现,线程每次不管怎么运行都是先执行完threading1线程,再去执行threading2线程,而这完全得益于joIn()函数:
我们来看源码是怎么解释join()的:
等待直到线程终止。这将阻塞调用线程,直到join()
被调用方法的线程终止(正常或通过未处理的异常终止),或者直到发生可选的超时。
讲完join():
我们再来认识一个有趣的参数daemon->守护线程:
先看源码:
daemon用'来指示线程是否是守护线程,必须在线程start()方法调用之前设置,否则会引发RunTimeError,当不存在活动的非守护线程时将退出python程序
演示daemon:
正常默认daemon为False:
可以看到主线程运行结束后退出后子线程继续运行并输出了内容,
但是现在如果有个需求要求我们实现主线程退出后必须kill掉子线程那么,如何实现这个需求,这就用到了daemon,我们只需要设置为True:
主线程运行结束后并没有等待子线程
运行完毕就kill掉了子线程没有输出finsh打印就已经结束了子线程了
# 多线程实现方式二,继承Thread 类,重写run方法:
这是一种很基本的写法。实际开发过程我们会涉及到类的调用以及类的方法引用写法会发生改变:
这里实现了在线程外部定义一个类,其中类的方法test作为一个可调用对象传给了继承了Thread并重写run方法的MyCallable类,这里留一个思考题,对于以上重写run你会发现我们的run是无法实现结果回调的
这就意味着,我们需要根据实际场景使用不同的模块处理不同的需求,可以给大家一个小提示可以使用concurrent.futures或者使用 queue.Queue()来实现结果回调,因为在queue源码中,它是基于deque来实现的而deque是线程安全的也就意味queue也是线程安全的,有兴趣的可以自己去看下
j结语:
python threading2种调用方式实例的更多相关文章
- Python包模块化调用方式详解
Python包模块化调用方式详解 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一般来说,编程语言中,库.包.模块是同一种概念,是代码组织方式. Python中只有一种模块对象类型 ...
- 【转】SVG与HTML、JavaScript的三种调用方式
原文:https://www.cnblogs.com/guohu/p/5085045.html SVG与HTML.JavaScript的三种调用方式 一.在HTMl中访问SVG的DOM 1 2 3 4 ...
- 【转载】Redis的Java客户端Jedis的八种调用方式(事务、管道、分布式…)介绍
转载地址:http://blog.csdn.net/truong/article/details/46711045 关键字:Redis的Java客户端Jedis的八种调用方式(事务.管道.分布式…)介 ...
- 同步(Sync)/异步(Async),阻塞(Block)/非阻塞(Unblock)四种调用方式
1. 概念理解 在进行网络编程时,我们常常见到同步(Sync)/异步(Async),阻塞(Block)/非阻塞(Unblock)四种调用方式: 同步/异步主要针对C端: 同步: ...
- python 线程的调用方式
python 线程的调用方式 #!/usr/bin/env python #-*- coding:utf-8 -*- # author:leo # datetime:2019/5/24 9:44 # ...
- Javascript中函数的四种调用方式
一.Javascript中函数的几个基本知识点: 1.函数的名字只是一个指向函数的指针,所以即使在不同的执行环境,即不同对象调用这个函数,这个函数指向的仍然是同一个函数. 2.函数中有两个特殊的内部属 ...
- 浅谈js函数三种定义方式 & 四种调用方式 & 调用顺序
在Javascript定义一个函数一般有如下三种方式: 函数关键字(function)语句: function fnMethodName(x){alert(x);} 函数字面量(Function Li ...
- Vue组件的三种调用方式
最近在写fj-service-system的时候,遇到了一些问题.那就是我有些组件,比如Dialog.Message这样的组件,是引入三方组件库,比如element-ui这样的,还是自己实现一个?虽然 ...
- magento 列表页显示产品属性值的几种调用方式
之前有人提到要在列表显示一些特定的属性,除了自带的名字,价格等.因为列表页和产品页都有一个同名的产品对象:$_product,而在产品页,$_product是直接可以用$_product->ge ...
随机推荐
- centos7使用fdisk:创建和维护MBR分区表
1.在VMware选择要添加硬盘的虚拟机,添加一块硬盘. 这样就有两块硬盘 2.重启虚拟机. cd /dev #dev是设备目录,下面有很多很多设备,其中就包含硬盘 ll grep | sd #过滤s ...
- 使用font-weight无法调节字体粗细的问题解决
最近我遇到这样的问题,就是使用font-weight无法调节字体粗细. 据我所知,font-weight是用于调节字体粗细的,可选100.200.300.400(normal).500.600.700 ...
- idea websorm 激活码(2020-1-6 实测可用)最新
2019年1月6日用 ZSI6IiIsImFzc2lnbmVlRW1haWwiOiIiLCJsaWNlbnNlUmVzdHJpY3Rpb24iOiIiLCJjaGVja0NvbmN1cnJlbnR ...
- sqlserver 批量修改数据库表主键名称为PK_表名
1.我们在创建sqlserver得数据表的主键的时候,有时会出现,后面加一串随机字符串的情况,如图所示: 2.如果你有强迫症的话,可以使用以下sql脚本进行修改,将主键的名称修改为PK_表名. --将 ...
- 开发者的拯救者还是掘墓人?解密低代码开发平台 ZT
据英国<金融时报>消息称,私募股权投资机构 KKR 和高盛共同筹集了 3.6 亿美元,以收购低代码开发平台 OutSystems 的“大量”少数股权,本次交易对 OutSystems 的估 ...
- 转:静态链表及其创建(C语言实现)
http://c.biancheng.net/view/3339.html 折半插入排序算法(C语言代码实现) http://c.biancheng.net/view/3440.html 二叉树层次遍 ...
- BZOJ #2506. calc [根号分治,莫队,二分]
\(p\) 是个正常范围, \(\sqrt p <= 100\) 比较小,预处理出来 \(a_i % p == k\) 的位置,然后丢进去,最后询问的 \(p\) 如果大于 \(100\) 就莫 ...
- Mac上的屏幕截图不起作用该如何修复?
屏幕截图是Mac提供的内置功能,很少有它不起作用.但是由于某些意外的设置或硬件问题,Mac上的屏幕截图有时无法正常工作,这里提供的是Mac上的屏幕截图不起作用该如何修复? 1.在Mac上启用屏幕快照快 ...
- 关于学习java虚拟机的知识整理一:jvm内存区域
之前由于考研,对于虚拟机的认识疏忽了太多,现在重新整理回顾一下. 如上图所示,jvm的内存区域(运行时数据区)共分为5处:方法区(Method Area).虚拟机栈(vm Stack).本地方法栈(N ...
- 按钮控制彩灯实验 CSU - 1770 树状数组 差分变单点修改
#include<iostream> #include<algorithm> #include<cstring> using namespace std; ; in ...