博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
python多线程编程-queue模块和生产者-消费者问题
阅读量:5761 次
发布时间:2019-06-18

本文共 2673 字,大约阅读时间需要 8 分钟。

摘录python核心编程

本例中演示生产者-消费者模型:商品或服务的生产者生产商品,然后将其放到类似队列的数据结构中。生产商品中的时间是不确定的,同样消费者消费商品的时间也是不确定的。

使用queue模块(python2.x版本中,叫Queue)来提供线程间通信的机制,从而让线程之间可以分享数据。具体而言,就是创建一个队列,让生产者(线程)在其中放入新的商品,而消费者(线程)消费这些商品。

下表是queue模块的部分属性:

属性 描述
queue模块的类
Queue(maxsize=0) 创建一个先入先出队列。如果给定最大值,则在队列没有空间时阻塞;否则,为无限队列
LifoQueue(maxsize=0) 创建一个后入先出队列。如果给定最大值,则在队列没有空间时阻塞;否则,为无限序列
PriorityQueue(maxsize=0) 创建一个优先级队列。如果给定最大值,则在队列没有空间时阻塞;否则,为无限序列
queue异常
Empty 当对空队列调用get*()方法时抛出异常
Full 当对已满的队列调用put*()方法时抛出异常
queue对象方法
qsize() 返回队列大小。(由于返回队列大小时可能被其他线程修改,所以该值为近似值)
empty() 如果队列为空,则返回True,否则返回False
full() 如果队列已满,则返回True,否则返回False
put(item,block=True,timeout=None) 将item放入队列。如果block为True(默认值),且timeout为None,则在有可用空间之前阻塞;如果timeout为正值,最多阻塞timeout秒;如果block为False,则抛出Empty异常
put_nowait(item) 和put(item,False)效果相同
get(block=True,timeout=None) 从队列上取得元素。如果给定了block(非0),则一直阻塞直到有可用的元素为止
get_nowait() 和get(False)效果想用
task_done() 用于表示队列中的某个元素已执行完成,该方法会被下面的join()使用
join() 在队列中所有元素执行完毕并调用上面的task_done()信号前,保持阻塞。

下面的prodcons.py脚本中使用了queue对象实现了生产者-消费者场景,随机生产或消费商品,且生产者和消费者独立、并发的执行线程。注意,这里使用了在之前章节中改写的

#python 3.6from random import randintfrom time import sleepfrom queue import Queuefrom myThread import MyThread#将一个对象放入队列中def writeQ(queue):    print('正在为队列生产………')    queue.put('商品',1)    print('当前商品总数:',queue.qsize())#消费队列中的一个对象    def readQ(queue):    val = queue.get(1)    print('正在从队列中消费商品……消费后还剩余商品:',queue.qsize())#模仿生产者。    def writer(queue,loops):    for i in range(loops):        writeQ(queue)        sleep(randint(1,3))#writer的睡眠时间一般比reader短,是为了阻碍 reader从空队列中获取对象,换句话说就是使得轮到reader执行时,已存在可消费对象的可能性更大。#模仿消费者    def reader(queue,loops):    for i in range(loops):        readQ(queue)        sleep(randint(2,5))    funcs = [writer,reader]nfuncs = range(len(funcs))def main():    nloops = randint(2,5)#randint 和randrange类似,区别在于,randrange是半开半闭区间,而randint是闭区间    q = Queue(32)        threads = []#模拟线程池    for i in nfuncs:        t = MyThread(funcs[i],(q,nloops),funcs[i].__name__)#创建线程        threads.append(t)            for i in nfuncs:        threads[i].start()  #开始执行线程            for i in nfuncs:        threads[i].join()            print('结束')    if __name__ == '__main__':    main()

执行效果类似:

PS C:\Users\WC> python E:\Python3.6.3\workspace\prodcons.py开始执行 writer  在: Thu Apr 19 21:06:22 2018正在为队列生产………开始执行 reader  在: Thu Apr 19 21:06:22 2018当前商品总数: 1正在从队列中消费商品……消费后还剩余商品: 0正在为队列生产………当前商品总数: 1正在从队列中消费商品……消费后还剩余商品: 0正在为队列生产………当前商品总数: 1正在从队列中消费商品……消费后还剩余商品: 0正在为队列生产………当前商品总数: 1正在为队列生产………当前商品总数: 2writer 结束于: Thu Apr 19 21:06:30 2018正在从队列中消费商品……消费后还剩余商品: 1正在从队列中消费商品……消费后还剩余商品: 0reader 结束于: Thu Apr 19 21:06:39 2018结束

 

posted on
2018-04-19 21:10 阅读(
...) 评论(
...)

转载于:https://www.cnblogs.com/hiwuchong/p/8886277.html

你可能感兴趣的文章
Oracle将NetBeans交给了Apache基金会
查看>>
填坑记:Uncaught RangeError: Maximum call stack size exceeded
查看>>
《中国人工智能学会通讯》——11.60 安全隐私感知的移动 App 推荐方法
查看>>
SpringCloud之消息总线(Spring Cloud Bus)(八)
查看>>
DLA实现跨地域、跨实例的多AnalyticDB读写访问
查看>>
(十)Java B2B2C o2o多用户商城 springcloud架构 高可用的服务注册中心
查看>>
Mvp官方示例
查看>>
如何在网站中加入百度统计
查看>>
推荐系统架构设计与实现
查看>>
PHP:第一章——PHP中的变量002
查看>>
LPDMvvmKit 系列之 UITableView 的改造
查看>>
通用智能传感集线器(Sensorhub)介绍
查看>>
使用Quick BI 制作企业数据分析报表
查看>>
如何成为一个优秀的WEB前端开发工程师?广州牵引力这样说
查看>>
JavaScript 之对象拷贝与赋值
查看>>
学习ui设计软件有哪些
查看>>
Github配置ssh链接win、mac
查看>>
垃圾邮件的一种应对方法
查看>>
补间动画与帧动画简单笔记
查看>>
Java集合之ArrayList源码解析
查看>>