Python threading模块condition原理及运行流程详解


Posted in Python onOctober 05, 2020

Condition的处理流程如下:

首先acquire一个条件变量,然后判断一些条件。

  • 如果条件不满足则wait;
  • 如果条件满足,进行一些处理改变条件后,通过notify方法通知其他线程,其他处于wait状态的线程接到通知后会重新判断条件。
  • 不断的重复这一过程,从而解决复杂的同步问题。

Condition的基本原理如下:

可以认为Condition对象维护了一个锁(Lock/RLock)和一个waiting池。线程通过acquire获得Condition对象,当调用wait方法时,线程会释放Condition内部的锁并进入blocked状态,同时在waiting池中记录这个线程。当调用notify方法时,Condition对象会从waiting池中挑选一个线程,通知其调用acquire方法尝试取到锁。

Condition对象的构造函数可以接受一个Lock/RLock对象作为参数,如果没有指定,则Condition对象会在内部自行创建一个RLock。

除了notify方法外,Condition对象还提供了notifyAll方法,可以通知waiting池中的所有线程尝试acquire内部锁。由于上述机制,处于waiting状态的线程只能通过notify方法唤醒,所以notifyAll的作用在于防止有的线程永远处于沉默状态。

演示条件变量同步的经典问题是生产者与消费者问题:假设有一群生产者(Producer)和一群消费者(Consumer)通过一个市场来交互产品。生产者的”策略“是如果市场上剩余的产品少于1000个,那么就生产100个产品放到市场上;而消费者的”策略“是如果市场上剩余产品的数量多余100个,那么就消费3个产品。用Condition解决生产者与消费者问题的代码如下:

# -*- coding: utf-8 -*-
"""
Created on Wed Nov 28 17:15:29 2018

@author: 18665
"""

import threading
import time

class Producer(threading.Thread):
  # 生产者函数
  def run(self):
    global count
    while True:
      if con.acquire():
        # 当count 小于等于1000 的时候进行生产
        if count > 1000:
          con.wait()
        else:
          count = count+100
          msg = self.name+' produce 100, count=' + str(count)
          print(msg)
          # 完成生成后唤醒waiting状态的线程,
          # 从waiting池中挑选一个线程,通知其调用acquire方法尝试取到锁
          con.notify()
        con.release()
        time.sleep(1)

class Consumer(threading.Thread):
  # 消费者函数
  def run(self):
    global count
    while True:
      # 当count 大于等于100的时候进行消费
      if con.acquire():
        if count < 100:
          con.wait()
        
        else:
          count = count-5
          msg = self.name+' consume 5, count='+str(count)
          print(msg)
          con.notify()
          # 完成生成后唤醒waiting状态的线程,
          # 从waiting池中挑选一个线程,通知其调用acquire方法尝试取到锁
        con.release()
        time.sleep(1)

count = 500
con = threading.Condition()

def test():
  for i in range(2):
    p = Producer()
    p.start()
  for i in range(5):
    c = Consumer()
    c.start()
if __name__ == '__main__':
  test()

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python实现数通设备端口使用情况监控实例
Jul 15 Python
Python首次安装后运行报错(0xc000007b)的解决方法
Oct 18 Python
TensorFlow损失函数专题详解
Apr 26 Python
使用 Python 实现文件递归遍历的三种方式
Jul 18 Python
python中对数据进行各种排序的方法
Jul 02 Python
利用Python绘制Jazz网络图的例子
Nov 21 Python
python 求10个数的平均数实例
Dec 16 Python
python字典和json.dumps()的遇到的坑分析
Mar 11 Python
python对一个数向上取整的实例方法
Jun 18 Python
python Matplotlib数据可视化(2):详解三大容器对象与常用设置
Sep 30 Python
利用python绘制正态分布曲线
Jan 04 Python
python 可视化库PyG2Plot的使用
Jan 21 Python
Python urllib库如何添加headers过程解析
Oct 05 #Python
Python3获取cookie常用三种方案
Oct 05 #Python
Python collections.deque双边队列原理详解
Oct 05 #Python
Python全局变量与global关键字常见错误解决方案
Oct 05 #Python
Python定时任务框架APScheduler原理及常用代码
Oct 05 #Python
Python xmltodict模块安装及代码实例
Oct 05 #Python
Python pathlib模块使用方法及实例解析
Oct 05 #Python
You might like
php重定向的三种方法分享
2012/02/22 PHP
详解cookie验证的php应用的一种SSO解决办法
2017/10/20 PHP
针对thinkPHP5框架存储过程bug重写的存储过程扩展类完整实例
2018/06/16 PHP
PHP一致性hash分布式算法封装类定义与用法示例
2018/08/04 PHP
(function(){})()的用法与优点
2007/03/11 Javascript
jquery select(列表)的操作(取值/赋值)
2009/08/06 Javascript
WEB高性能开发之疯狂的HTML压缩
2010/06/19 Javascript
JQuery.ajax传递中文参数的解决方法 推荐
2011/03/28 Javascript
jQuery操作checkbox选择(list/table)
2013/04/07 Javascript
JavaScript定义类和对象的方法
2014/11/26 Javascript
使用javascript实现简单的选项卡切换
2015/01/09 Javascript
使用Sticky组件实现带sticky效果的tab导航和滚动导航的方法
2016/03/22 Javascript
使用AJAX实现Web页面进度条的实例分享
2016/05/06 Javascript
Bootstrap组件系列之福利篇几款好用的组件(推荐)
2016/06/23 Javascript
js实现图片360度旋转
2017/01/22 Javascript
ES6新特性之变量和字符串用法示例
2017/04/01 Javascript
Vue实现点击时间获取时间段查询功能
2020/08/21 Javascript
vue axios 给生产环境和发布环境配置不同的接口地址(推荐)
2018/05/08 Javascript
jQuery实现开关灯效果
2020/08/02 jQuery
使用Python实现简单的服务器功能
2017/08/25 Python
在PyCharm下打包*.py程序成.exe的方法
2018/11/29 Python
Python: 传递列表副本方式
2019/12/19 Python
python使用openpyxl操作excel的方法步骤
2020/05/28 Python
Python xpath表达式如何实现数据处理
2020/06/13 Python
python pandas dataframe 去重函数的具体使用
2020/07/20 Python
Python利用命名空间解析XML文档
2020/08/10 Python
python中的插入排序的简单用法
2021/01/19 Python
html5的画布canvas——画出简单的矩形、三角形实例代码
2013/06/09 HTML / CSS
大都会艺术博物馆商店:The Met Store
2018/06/22 全球购物
SQL SERVER面试资料
2013/03/30 面试题
自我鉴定怎么写
2013/12/05 职场文书
《蚂蚁和蝈蝈》教学反思
2014/02/24 职场文书
经济贸易专业自荐信
2014/06/11 职场文书
拾金不昧表扬信怎么写
2015/05/04 职场文书
对学校的意见和建议
2015/06/04 职场文书
统招统分证明
2015/06/23 职场文书