python多线程Lock和RLock的区别

1. 两种锁的不同

1.1 定义

为了确保对共享资源的访问,python提供了两种锁,一个是上一篇提到的Lock,还有一个就是RLock,他们的区别在于:

Lock是可用的最低级别的同步指令,一个线程只能请求一次,而RLock是可以被一个线程请求多次的同步指令

当Lock处于锁定状态时,不被特定的线程所拥有,而RLock使用了“拥有的线程”和“递归等级”的概念,因此处于锁定状态时,可以被线程拥有

1.2 死锁

Lock在下面的情形下会发生死锁

Lock.acquire()

Lock.acquire()

Lock.release()

Lock.release()

连续两次acquire请求,会导致死锁,因为第一次获得锁之后还没有释放时,第二次acquire请求紧接着就到来,可是acquire会让程序阻塞,无法执行release(),这就导致锁永远无法释放,死锁是非常危险非常严重的问题

1.3 可重入锁

RLock就不存在1.2中所提到的死锁问题

RLock.acquire()

RLock.acquire()

RLock.release()

RLock.release()

不过要保证有多少次acquire(),就有多少次release()

2. 怎么会多次请求锁呢?

最初接触到Lock和RLock这两者之间的不同之处时,感到十分困惑。RLock的优势在于,在同一个线程里可以多次申请锁,而Lock则不能,必须在释放之后才能再次申请,那么,这样做也没问题啊,不会出现第一次申请后,在释放前又申请的可能啊,在编写代码的时候,完全可以认为的控制这种情况的发生。

然而事实并非如此,我现在假设一种情形,使得死锁的发生不可避免

import threading

m_lock = threading.Lock()

def h():

with m_lock:

print('h')

def g():

with m_lock:

print('g')

h()

g()

上面的例子中,h()和g()中都用了Lock,在多线程环境下,他们可以做到相安无事,但是,程序的结构总是处于变化中,尤其是那些庞大的系统,一个小小的变化可能牵一发而动全身,假设发生了下面的变化

import threading

m_lock = threading.Lock()

# m_lock = threading.RLock()

def h():

with m_lock:

g()

print('h')

def g():

with m_lock:

print('g')

h()

g()

在h()函数中,获得锁以后要执行g(),那么此时,程序就会发生死锁,在大的项目里,情况会比这更加复杂,你很难通过眼前的几行代码发现这种死锁的情况,因为很可能发生死锁的地方是在很深层次的调用过程中,因此,使用RLock是非常安全的选择.

执行上面的代码,程序不会输出任何信息,也永远不会结束,因为已经发生了死锁,将注释的Lock替换成RLock,程序立马可以执行

python lock_python多线程Lock和RLock的区别相关推荐

  1. python中的Lock与RLock

    首先讲解不加锁在多线程中会导致的问题,然后用实例说明如何通过加锁让函数变为线程安全的函数.也通过实例说明了RLock和Lock的区别:在同一线程内,对RLock进行多次acquire()操作,程序不会 ...

  2. python线程安全的计数器_Python多线程同步Lock、RLock、Semaphore、Event实例

    一.多线程同步 由于CPython的python解释器在单线程模式下执行,所以导致python的多线程在很多的时候并不能很好地发挥多核cpu的资源.大部分情况都推荐使用多进程. python的多线程的 ...

  3. 【记录】python多线程的使用 线程同步(LOCK和RLOCK) python与mysql数据库交互实现增加和查找 python的格式化输出

    文章目录 多线程: _thread模块 threading模块: 线程同步(LOCK和RLOCK) 和mysql交互: 附:python的格式化输出 附录 多线程: _thread模块 例一 impo ...

  4. educoder 使用线程锁(lock)实现线程同步_Python并行编程(二):多线程锁机制利用Lock与RLock实现线程同步

    什么是锁机制? 要回答这个问题,我们需要知道为什么需要使用锁机制.前面我们谈到一个进程内的多个线程的某些资源是共享的,这也是线程的一大优势,但是也随之带来一个问题,即当两个及两个以上的线程同时访问共享 ...

  5. java多线程:9、synchronized、Lock的底层实现原理以及和volatile、Lock、ReentrantLock的区别?

    文章目录 0.1.线程中安全性问题的体现: 0.2.线程安全问题的解决办法 1.synchronized的底层实现原理分析 2.Lock的底层实现原理分析? 3.synchronized和volati ...

  6. python多核多线程编程实例_Python多线程

    多线程基础概念 并行与并发并行:同时处理多个任务,必须在多核环境下 一段时间内同时处理多个任务,单核也可以并发 并发手段线程:内核空间的调度 进程:内核空间的调度 协程:用户空间的调度 线程可以允许程 ...

  7. python实现多线程

    文章目录 1 线程基本概念 1.1 线程是什么? 1.2 线程和进程关系? 2 Python线程模块 3 线程间同步 4 线程池 4.1 传统多线程问题? 4.2 线程池基本原理: 5 协程 5.2 ...

  8. python学习——多线程

    python学习--多线程 概念 python中线程的开发 线程的启动 线程的退出和传参 threading的属性和方法 threading实例的属性和方法 多线程 daemon线程和non-demo ...

  9. python --- 基础多线程编程

    在python中进行多线程编程之前必须了解的问题: 1. 什么是线程? 答:线程是程序中一个单一的顺序控制流程.进程内一个相对独立的.可调度的执行单元,是系统独立调度和分派CPU的基本单位指运行中的程 ...

最新文章

  1. WP8:Unity3D之间的值传递
  2. 刷前端面经笔记(七)
  3. JDK11的新特性:新的HTTP API
  4. Asp.Net 设计模式 之 “简单工厂”模式
  5. 数据结构(三):非线性逻辑结构-树
  6. python软件下载3版本-Python3.9下载
  7. 09. 慎重选择删除元素的方法
  8. java中utf8转成gbk,java中GBK转UTF-8乱码的解决方法
  9. 汇编 - 实验 - 计算X+(Y-Z)=W
  10. 如何设置点击listview的任何位置都可以选中checkbook
  11. 彼得林奇的成功投资三——回购+提高股息+无多元化
  12. jQuery读书笔记
  13. Python类和对象以及继承多态(超详细,小白也可以懂)
  14. 2k 幻14_华硕幻14(2060 2k版)值得入手吗?
  15. matlab gevfit,基于MATLAB和Scipy-GEV-fi的不同参数估计
  16. Mac 安装element-ui
  17. 网易游戏 Flink SQL 平台化实践
  18. 耐心排序之最长递增子序列(LIS)
  19. python 字符串输出报错 'utf-8' codec can't encode characters in position
  20. 示波器探头校准-补偿电容

热门文章

  1. JDK 12开关表达式遇到意外的枚举值
  2. Java 11将包含更多功能
  3. jbpm小项目测试_尝试使用jBPM Console NG(测试版)
  4. java集合的功能_功能性Java集合
  5. 应用JDK 9 @不推荐使用的增强功能
  6. 介绍Spring Integration
  7. ehcache rmi_EhCache复制:RMI与JGroups
  8. Spring Integration Framework简介
  9. Spring @Configuration – RabbitMQ连接
  10. Java DB中的Java用户定义类型(UDT)