2线程的使用方法
  (1)锁机制
       递归锁
           RLock()    可以有无止尽的锁,但是会有一把万能钥匙
       互斥锁:
           Lock()     一把钥匙配一把锁
       GIL:全局解释器锁
          锁的是线程,是CPython解释器上的一个锁,锁的是线程,意思是在同一时间只允许一个线程访问cpu
代码:

from threading import Thread,RLockimport time,os# RLock是递归锁 --- 是无止尽的锁,但是所有锁都有一个共同的钥匙# 想解决死锁,配一把公共的钥匙就可以了。

def man(l_tot,l_pap):    l_tot.acquire()# 是男的获得厕所资源,把厕所锁上了    print('alex在厕所上厕所')    time.sleep(1)    l_pap.acquire()# 男的拿纸资源    print('alex拿到卫生纸了!')    time.sleep(0.5)    print('alex完事了!')    l_pap.release()# 男的先还纸    l_tot.release()# 男的还厕所

def woman(l_tot,l_pap):    l_pap.acquire()  # 女的拿纸资源    print('小雪拿到卫生纸了!')    time.sleep(1)    l_tot.acquire()  # 是女的获得厕所资源,把厕所锁上了    print('小雪在厕所上厕所')    time.sleep(0.5)    print('小雪完事了!')    l_tot.release()  # 女的还厕所    l_pap.release()  # 女的先还纸

if __name__ == '__main__':    l_tot = l_pap = RLock()    t_man = Thread(target=man,args=(l_tot,l_pap))    t_woman = Thread(target=woman,args=(l_tot,l_pap))    t_man.start()    t_woman.start()

死锁代码:
from threading import Thread,Lockimport time,os

def man(l_tot,l_pap):    l_tot.acquire()# 是男的获得厕所资源,把厕所锁上了    print('alex在厕所上厕所')    time.sleep(1)    l_pap.acquire()# 男的拿纸资源    print('alex拿到卫生纸了!')    time.sleep(0.5)    print('alex完事了!')    l_pap.release()# 男的先还纸    l_tot.release()# 男的还厕所

def woman(l_tot,l_pap):    l_pap.acquire()  # 女的拿纸资源    print('小雪拿到卫生纸了!')    time.sleep(1)    l_tot.acquire()  # 是女的获得厕所资源,把厕所锁上了    print('小雪在厕所上厕所')    time.sleep(0.5)    print('小雪完事了!')    l_tot.release()  # 女的还厕所    l_pap.release()  # 女的先还纸

if __name__ == '__main__':    l_tot = Lock()    l_pap = Lock()    t_man = Thread(target=man,args=(l_tot,l_pap))    t_woman = Thread(target=woman,args=(l_tot,l_pap))    t_man.start()    t_woman.start()

(2) 信号量:
      from threading import Semaphore
      去看多进程的信号量

代码:

from threading import Semaphore,Threadimport time

def func(sem,i):    sem.acquire()    print('第%s个人进入屋子'%i)    time.sleep(2)    print('第%s个人离开屋子'%i)    sem.release()

sem = Semaphore(20)for i in range(20):    t = Thread(target=func,args=(sem,i))    t.start()

(3) 事件
      from threading import Event
      去看多进程的事件机制

代码:

from threading import Thread,Eventimport time,random

def conn_mysql(e,i):    count = 1    while count <= 3:        if e.is_set():            print('第%s个人连接成功!'%i)            break        print('正在尝试第%s次重新连接...'%(count))        e.wait(0.5)        count += 1

def check_mysql(e):    print('\033[42m 数据库正在维护 \033[0m')    time.sleep(random.randint(1,2))    e.set()

if __name__ == '__main__':    e = Event()    t_check = Thread(target=check_mysql,args=(e,))    t_check.start()

    for i in range(10):        t_conn = Thread(target=conn_mysql,args=(e,i))        t_conn.start()

(4) 条件
      from threading import Condition
      条件是让程序员自行去调度线程的一个机制
      # Condition涉及4个方法
      # acquire()
      # release()
      # wait()    是指让线程阻塞住
      # notify(int)  是指给wait发一个信号,让wait变成不阻塞
      #     int是指,你要给多少给wait发信号

代码:

from threading import Thread,Conditionimport time# Condition涉及4个方法# acquire()# release()# wait()    是指让线程阻塞住# notify(int)  是指给wait发一个信号,让wait变成不阻塞#     int是指,你要给多少给wait发信号

def func(con,i):    con.acquire()    con.wait()# 线程执行到这里,会阻塞住,等待notify发送信号,来唤醒此线程    con.release()    print('第%s个线程开始执行了!'%i)

if __name__ == '__main__':    con = Condition()    for i in range(10):        t = Thread(target=func,args=(con,i))        t.start()    while 1:        num = int(input(">>>"))        con.acquire()        con.notify(num)# 发送一个信号给num个正在阻塞在wait的线程,让这些线程正常执行        con.release()另一种解释是:
from threading import Condition,Threadimport time

def func(con,i):    con.acquire()# 主线程和10个子线程都在抢夺递归锁的一把钥匙。    # 如果主线程抢到钥匙,主线程执行while 1,input,然后notify发信号,还钥匙。但是,此时如果主线程执行特别快    # 极有可能接下来主线程又会拿到钥匙,那么此时哪怕其他10个子线程的wait接收到信号,但是因为没有拿到钥匙,所以其他子线程还是不会执行    con.wait()    print('第%s个线程执行了'%i)    con.release()con = Condition()for i in range(10):    t = Thread(target=func,args = (con,i))    t.start()while 1:    # print(123)    con.acquire()    num = input('>>>')    con.notify(int(num))    con.release()    time.sleep(0.5)

# 条件 涉及 4个方法:#    con.acquire()#    con.release()#    con.wait()  # 假设有一个初始状态为False,阻塞。一旦接受到notify的信号后,变为True,不再阻塞#    con.notify(int)  给wait发信号,发int个信号,会传递给int个wait,让int个线程正常执行
 

(5) 定时器
      from threading import Timer
          # Timer(time,func)
          # time:睡眠的时间,以秒为单位
          # func:睡眠时间之后,需要执行的任务

代码:

from threading import Timer# 定时器

def func():    print('就是这么nb!')

Timer(2.5,func).start()# Timer(time,func)# time:睡眠的时间,以秒为单位# func:睡眠时间之后,需要执行的任务

线程使用方法 锁(lock,Rlock),信号了(Semaphore),事件(Event),条件(Ccndition),定时器(timer)的更多相关文章

  1. python笔记10-多线程之线程同步(锁lock)

    前言 关于吃火锅的场景,小伙伴并不陌生,吃火锅的时候a同学往锅里下鱼丸,b同学同时去吃掉鱼丸,有可能会导致吃到生的鱼丸. 为了避免这种情况,在下鱼丸的过程中,先锁定操作,让吃火锅的小伙伴停一会,等鱼丸 ...

  2. 线程锁Lock ,Rlock

    锁的引入: 我们查看官方文档:https://docs.python.org/3/library/threading.html#lock-objects 原语锁:threading.Lock 实现原始 ...

  3. python 多线程中的同步锁 Lock Rlock Semaphore Event Conditio

    摘要:在使用多线程的应用下,如何保证线程安全,以及线程之间的同步,或者访问共享变量等问题是十分棘手的问题,也是使用多线程下面临的问题,如果处理不好,会带来较严重的后果,使用python多线程中提供Lo ...

  4. 扯扯python的多线程的同步锁 Lock RLock Semaphore Event Condition

    我想大家都知道python的gil限制,记得刚玩python那会,知道了有pypy和Cpython这样的解释器,当时听说是很猛,也就意味肯定是突破了gil的限制,最后经过多方面测试才知道,还是那德行… ...

  5. python多线程锁lock/Rlock/BoundedSemaphore/Condition/Event

    import time import threading lock = threading.RLock() n = 10 def task(arg): # 加锁,此区域的代码同一时刻只能有一个线程执行 ...

  6. [b0039] python 归纳 (二四)_多进程数据共享和同步_锁Lock&RLock

    # -*- coding: utf-8 -*- """ 多进程 锁使用 逻辑: 10个进程各种睡眠2秒,然后打印. 不加锁同时打印出来,总共2秒,加锁一个接一个打印,总共 ...

  7. python全栈开发,Day42(Thread类的其他方法,同步锁,死锁与递归锁,信号量,事件,条件,定时器,队列,Python标准模块--concurrent.futures)

    昨日内容回顾 线程 什么是线程? 线程是cpu调度的最小单位 进程是资源分配的最小单位 进程和线程是什么关系? 线程是在进程中的一个执行单位 多进程 本质上开启的这个进程里就有一个线程 多线程 单纯的 ...

  8. python多线程编程—同步原语入门(锁Lock、信号量(Bounded)Semaphore)

    摘录python核心编程 一般的,多线程代码中,总有一些特定的函数或者代码块不希望(或不应该)被多个线程同时执行(比如两个线程运行的顺序发生变化,就可能造成代码的执行轨迹或者行为不相同,或者产生不一致 ...

  9. 《Python》线程之锁、信号量、事件、条件、定时器、队列

    一.锁 线程为什么要有锁: += .-= 赋值操作数据不安全(要经过取值.计算.放回值,3部操作) pop .append 都是数据安全的(只有添加和删除,一次操作) 队列也是数据安全的 1.同步锁 ...

随机推荐

  1. 20155328 2016-2017-2 《Java程序设计》第5周学习总结

    教材学习内容总结 程序设计本身的错误,建议使用Exception或其子类实例来表现. Java中所有错误都会被打包成对象. 如果父类异常对象在子类异常对象前被捕捉,则catch子类异常对象的区块将永远 ...

  2. B. Beautiful Paintings

    time limit per test 1 second memory limit per test 256 megabytes input standard input output standar ...

  3. hdu1087 dp(最大上升子序列和)

    题意,给出一列数,要求所有上升子序列中序列和最大的. 这回不是求长度了,但是还是相当基础的 dp 水题,只要用 dp [ q ] 记录以 第 q 个数 a [ q ] 为结尾的上升子序列的最大的和就可 ...

  4. jquery选择器总结2

    1.JQuery的概念 JQuery是一个JavaScript的类库,这个类库集合了很多功能方法,利用类库你可以用一些简单的代码实现一些复杂的JS效果. 2.JQuery实现了 代码的分离 不用再网页 ...

  5. Laravel 5.1 中 Session 数据存储、访问、删除及一次性Session实例教程

    1.Session的由来及其实现 HTTP协议是无状态的协议,同一个客户端的这次请求和上次请求是没有对应关系的.也就是说我们无法在服务器端确认两次请求是否是同一个用户所为,这为我们在一些应用场景中实现 ...

  6. Apache和Nginx的Rewrite规则对比

    一.Apache的rewrite 1.Rewrite规则简介: Rewirte主要的功能就是实现URL的跳转,它的正则表达式是基于Perl语言.可基于服务器级的(httpd.conf)和目录级的(.h ...

  7. 协程、gevent实现异步io、进程、线程、协程对比

    异步io的说白了就是遇到io操作的时候,就停下来去做别的事情.io分网络io和磁盘io,网络io比如说打开一个网站获取数据,下载一首歌等等,磁盘io就是把数据存到一个文件里面,写到磁盘上. 从网站上获 ...

  8. Jenkins进阶-远程构建任务(4)

    开发过程中提交代码以后,如何不登录Jenkins就自动触发jenkins 任务来发布软件版本. 1.首先我们创建一个Jenkins任务. 2.选择"构建触发器"->勾选&qu ...

  9. Word中回车和网页换行替换

    回车^p 换行^l 用编辑中的查找替换即可 查找^l,替换为^p (一)有建议说按Delete键一个一个将其删除,这是麻烦的,其实可用WORD的查找替换工具一次性替换成回车符.查找--点特殊字符--手 ...

  10. WinForm下ComboBox设定SelectedValue总结 (SelectedValue==null解决办法)[转]

    http://www.cnblogs.com/qqflying/archive/2013/05/23/3096050.html 实践发现:以SelectedIndex赋值让ComboBox自动选中时能 ...