Python线程操作
一、全局锁
1、在Python中,Python代码的执行由Python虚拟机来控制,而在Python虚拟机中,同一时刻只有一个线程在执行,就像单CPU的系统中运行多个进程那样,内存中可以存放多个程序,但在任意时刻,只有一个程序在CPU中运行。同样的,在Python解释器中可以“运行”多个线程,但在任意时刻,只有一个线程在Python解释器中运行。
2、对Python虚拟机的访问由全局解释器锁【GIL】来控制,正是这个锁能保证同一时刻只有一个线程在运行。
3、多线程环境中,Python虚拟机的执行方式为:
1. 设置GIL 2. 切换到一个线程去运行 3. 运行: a. 指定数量的字节码指令,或者 b. 线程主动让出控制(可以调用time.sleep(0)) 4. 把线程设置为睡眠状态 5. 解锁GIL 6. 再次重复以上所有步骤 |
二、线程模块
Python提供了【thread】和【threading】模块。在多线程编程中,建议使用【threading】模块,这是因为:
1、在【thread】模块中,当主线程退出时,其他没有被清除的线程没有运行结束就会被退出。但在【threading】模块中能确保所有的“重要的”子线程(这里的重要的子线程指的是守护线程)运行结束后,进程才会结束
2、在【threading】模块是更高级的线程模块,它不仅提供了Thread类,还提供了线程同步机制
thread模块
内建函数
1、thread.start_new_thread(function, args[, kwargs=None]) 这个函数用来启动一个线程,其参数含义分别为: function:线程任务函数 args:线程任务函数的参数【以元组的方式传入】 kwargs:可选的参数 2、thread.interrupt_main() 这个函数用来中断主线程 3、thread.exit() 这个函数用来退出线程 4、thread.get_ident() 这个函数用来获取线程标识号 5、thread.allocate_lock() 这个线程用来获取LockType对象 6、thread.stack_size([size]) 这个线程用来返回创建新线程栈容量,其参数含义为: size:指定创建新线程栈容量,该参数取值为0或不小于32,768(32KB) |
LockType对象
1、lock.acquire([waitflag]) 这个函数用来申请锁对象,若是获得锁对象返回True,否则返回False 2、lock.release() 这个函数用来释放锁对象【使用该函数前提是获取锁对象】 3、lock.locked() 这个函数用来获取对象锁的状态,若是已被锁住则返回True,否则返回False |
示例:
>>> import thread >>> sum = 0 /*****************线程任务函数**********************/ >>> def add(lock): global sum #设置为全局变量 lock.acquire() #加锁 i = 1 while(i < 3): sum = sum + 10 i = i + 1 id = thread.get_ident() #线程号 print "Thread ",id,"set sum = ",sum lock.release() #释放锁 /***********************启动线程**************************/ >>> def startTask(): lock = thread.allocate_lock() #申请锁对象 task_0 = thread.start_new_thread(add,(lock,)) task_1 = thread.start_new_thread(add,(lock,)) /************************测试**************************/ >>> startTask() >>> Thread 764 set sum = 20 Thread 5240 set sum = 40
threading模块
【threading】模块式以【thread】为基础,但提供更高的线程类以及同步机制。
内建函数
1、threading.activeCount() 这个函数用来获取【active Thread】的数目 2、threading.enumerate() 这个函数用来获取【active Thread】列表。注意:包括中断的线程以及还未开始的线程 3、threading.currentThread() 这个函数用来获取当前运行的【Thread object】 4、threading.settrace(func) 这个函数用来设置所有通过【threading】模块启动的线程的跟踪函数,该函数在【Thread Object】的【run】方法执行前被调用,其参数含义为: func:跟踪函数名 5、threading.setprofile(func) 这个函数用来设置所有通过【threading】模块启动的线程的profile函数 6、threading.Event() 这个工厂函数用来获取一个新的【Event Object】 7、threading.Lock() 这个工厂函数用来获取【LockType Object】 8、threading.RLock() 这个工厂函数用来获取【RLock Object】 9、threading.Condition() 这个工厂函数用来获取【Condition Object】 10、threading.Semaphore([value]) 这个工厂函数用来获取【Semaphore Object】 11、threading.BoundedSemaphore([value]) 这个工厂函数用来获取【Bounded Semaphore Object】 |
内建类
1、class threading.local 类似Java的ThreadLocal 2、class threading.Thread(group=None, target=None, name=None, args=(), kwargs={}) 构造函数参数含义如下: target:Thread类中【run】函数调用的函数 name:指定线程的名,默认线程名格式为:【Thread-N】 args:target函数的参数 1)、start() 启动线程,值得注意的是:该方法只能被线程调用一次,否则抛出异常RuntimeError 2)、run() 线程任务函数。常被子类重写,类似Java Thread类的run函数 3)、is_alive() 判断线程是否【alive】 4)、setDaemon() 将线程设置为守护线程 3、class threading.Timer(interval, function, args=[], kwargs={}) Timer类继承threading.Thread类,其参数含义为: interval:线程时间执行时间间隔,以秒为单位 function:Thread类中run函数执行的目标函数 args:目标函数的参数 1)、cancel() 取消Timer任务的执行 |
示例
/***************************Timer实例************************/ >>> def putOutNumber(): id = threading.currentThread().getName() print id,'Hello' >>> def startTimer(): timer = threading.Timer(60,putOutNumber) timer.start() >>> startTimer() >>> Thread-1 Hello /****************继承Thread与Semaphore实例********************/ >>> import threading >>> class MyThread(threading.Thread): def __init__(self,name,semaphore): threading.Thread.__init__(self,None,None,name,None) self.semaphore = semaphore def run(self): #override run function self.semaphore.acquire() i = 1 while(i < 3): print self.getName(),' print ',i i = i + 1 self.semaphore.release() >>> def startTask(): semaphore = threading.Semaphore() thread_0 = MyThread("Thread_0",semaphore) thread_1 = MyThread("Thread_1",semaphore) thread_0.start() thread_1.start() >>> startTask() >>> Thread_0 print 1 Thread_0 print 2 Thread_1 print 1 Thread_1 print 2 /*********************进程之间进行通信************************/ >>> class ManagerThread(threading.Thread): def __init__(self,name,event): threading.Thread.__init__(self,None,None,name,None) self.event = event def run(self): #override run function print self.getName(),' say ','go' self.event.set() >>> class PeopleThread(threading.Thread): def __init__(self,name,event): threading.Thread.__init__(self,None,None,name,None) self.event = event def run(self): self.event.wait() print self.getName(),' start ','go' >>> def startTask(): event = threading.Event() m_thread = ManagerThread("Manager",event) p_thread = PeopleThread("People",event) p_thread.start() m_thread.start() /*************************测试****************************/ >>> startTask() >>> Manager say go People start go
Mutex
内建类
1、class mutex.mutex mutex对象有两个属性:锁和队列。当锁没有被锁时,队列是空的。 /*********************mutex Object 函数********************/ 1)、mutex.test() 这个函数检测mutex是否被锁 2)、 mutex.testandset() 这个函数用来检测mutex是否被锁,若是没有锁住,则锁住并返回True,否则返回False。值得注意的是:这个函数是原子操作 3)、mutex.lock(function, argument) 这个函数用来执行函数function(argument)【前提是mutex没有被锁】。如果mutex锁被锁,则将function(argument)放入队列中 4)、mutex.unlock() 这个函数用来解锁mutex【前提是队列是空的】。如果队列不是空的,则在队列中取出第一个function(argument)执行并不解锁 |
示例
>>> import mutex >>> def putOutTask(text): print text >>> def startTask(): m_metux = mutex.mutex() m_metux.lock(putOutTask,'I am task_0') m_metux.lock(putOutTask,'T am task_1') m_metux.lock(putOutTask,'I am task_2') m_metux.lock(putOutTask,'T am task_3') m_metux.lock(putOutTask,'I am task_4') m_metux.lock(putOutTask,'T am task_5') while(m_metux.test()): m_metux.unlock() m_metux.unlock() /**************************测试***************************/ >>> startTask() I am task_0 T am task_1 I am task_2 T am task_3 I am task_4 T am task_5
Python线程操作的更多相关文章
- Python程序中的线程操作(线程池)-concurrent模块
目录 Python程序中的线程操作(线程池)-concurrent模块 一.Python标准模块--concurrent.futures 二.介绍 三.基本方法 四.ProcessPoolExecut ...
- [ python ] 线程的操作
目录 (见右侧目录栏导航) - 1. 前言 - 1.1 进程 - 1.2 有了进程为什么要有线程 - 1.3 线程的出现 - 1.4 进程和线程的关系 - 1.5 线程的 ...
- Python程序中的线程操作-创建多线程
目录 一.python线程模块的选择 二.threading模块 三.通过threading.Thread类创建线程 3.1 创建线程的方式一 3.2 创建线程的方式二 四.多线程与多进程 4.1 p ...
- python——线程与多线程进阶
之前我们已经学会如何在代码块中创建新的线程去执行我们要同步执行的多个任务,但是线程的世界远不止如此.接下来,我们要介绍的是整个threading模块.threading基于Java的线程模型设计.锁( ...
- Python 线程、进程和协程
python提供了两个模块来实现多线程thread 和threading ,thread 有一些缺点,在threading 得到了弥补,为了不浪费时间,所以我们直接学习threading 就可以了. ...
- [python] 线程简介
参考:http://www.cnblogs.com/aylin/p/5601969.html 我是搬运工,特别感谢张岩林老师! python 线程与进程简介 进程与线程的历史 我们都知道计算机是由硬件 ...
- Python 线程(threading) 进程(multiprocessing)
*:first-child { margin-top: 0 !important; } body>*:last-child { margin-bottom: 0 !important; } /* ...
- python线程同步原语--源码阅读
前面两篇文章,写了python线程同步原语的基本应用.下面这篇文章主要是通过阅读源码来了解这几个类的内部原理和是怎么协同一起工作来实现python多线程的. 相关文章链接:python同步原语--线程 ...
- Python 线程同步变量,同步条件,列队
条件变量同步 有一类线程需要满足条件之后才能够继续执行,Python提供了threading.Condition 对象用于条件变量线程的支持,它除了能提供RLock()或Lock()的方法外,还提供了 ...
随机推荐
- SpringBoot Redis序列化配置
Redis配置 #Redis spring.redis.host= spring.redis.port=6379 spring.redis.database=0 # Redis服务器连接密码(默认为空 ...
- Ubuntu系统用户与用户组
1.查看用户组 vi /etc/group 结果说明: 组名: 组名是用户组的名称,由字母或数字构成.与/etc/passwd中的登录名一样,组名不应重复. 口令: 口令字段存放的是用户组加密后的 ...
- session和xsrf
1.pip install pycket 2.pip install redis 防止xsrf攻击只需在模板form标签加入: {% module xsrf_form_html() %} <!D ...
- Linux/Android——input_handler之evdev (四) 【转】
转自:http://blog.csdn.net/u013491946/article/details/72638919 版权声明:免责声明: 本人在此发文(包括但不限于汉字.拼音.拉丁字母)均为随意敲 ...
- Yii操作数据库的3种方法
一.执行原生太SQL的PDO方式. 复制代码代码如下: $sql = "";//原生态sql语句 xx::model()->dbConnection->createCo ...
- python--optparse
import optparse op = optparse.OptionParser() op.add_option("--s", dest="server") ...
- 阿里云Ubuntu快速建站
阿里云Ubuntu快速建站 有一个小笑话: 从前有个程序员遇到了一个问题.他想,没事,我懂,用线程就好了.现他有两个问题了. 本人小白,对网站部署什么都不懂,只是申请个阿里云服务器,把我的站点放上去. ...
- Appium+python自动化10-AVD 模拟器【转载】
前言 有些小伙伴没android手机,这时候可以在电脑上开个模拟器玩玩 一.模拟器配置 1.双击启动AVD Manager,进入配置界面
- SPRING CLOUD服务网关之ZUUL
服务网关是微服务架构中一个不可或缺的部分.通过服务网关统一向外系统提供REST API的过程中,除了具备服务路由.均衡负载功能之外,它还具备了权限控制等功能.Spring Cloud Netflix中 ...
- C# Quartz 整理
因项目需要,在C#中使用了定时程序.自然就使用了Quartz了 但是使用的时候,经过一段时间后,发现了两个重大问题,结果导致的是一样的,就是都导致了定时不会继续执行了. 第一个问题是,定时程序发布在I ...