Queue

Queue是python标准库中的线程安全的队列(FIFO)实现,提供了一个适用于多线程编程的先进先出的数据结构,即队列,用来在生产者和消费者线程之间的信息传递

基本FIFO队列

class Queue.Queue(maxsize=0)

FIFO即First in First Out,先进先出。Queue提供了一个基本的FIFO容器,使用方法很简单,maxsize是个整数,指明了队列中能存放的数据个数的上限。一旦达到上限,插入会导致阻塞,直到队列中的数据被消费掉。如果maxsize小于或者等于0,队列大小没有限制。

举个例子:

 import Queue

 q = Queue.Queue()

 for i in range(5):
q.put(i) while not q.empty():
print q.get() 输出结果:
0
1
2
3
4

LIFO队列

class Queue.LifoQueue(maxsize=0)

LIFO即Last in First Out,后进先出。与栈的类似,使用也很简单,maxsize用法同上

举个例子:

 import Queue

 q = Queue.LifoQueue()

 for i in range(5):
q.put(i) while not q.empty():
print q.get() 输出: 4
3
2
1
0

可以看到仅仅是将Queue.Quenu类替换为Queue.LifiQueue类

优先级队列

class Queue.PriorityQueue(maxsize=0)

构造一个优先队列。maxsize用法同上。

import Queue
import threading class Job(object):
def __init__(self, priority, description):
self.priority = priority
self.description = description
print 'Job:',description
return
def __cmp__(self, other):
return cmp(self.priority, other.priority) q = Queue.PriorityQueue() q.put(Job(3, 'level 3 job'))
q.put(Job(10, 'level 10 job'))
q.put(Job(1, 'level 1 job')) def process_job(q):
while True:
next_job = q.get()
print 'for:', next_job.description
q.task_done() workers = [threading.Thread(target=process_job, args=(q,)),
threading.Thread(target=process_job, args=(q,))
] for w in workers:
w.setDaemon(True)
w.start() q.join()

输出结果:

Job: level 3 job
Job: level 10 job
Job: level 1 job
for: level 1 job
for: level 3 job
for: job: level 10 job

一些常用方法

task_done()

意味着之前入队的一个任务已经完成。由队列的消费者线程调用。每一个get()调用得到一个任务,接下来的task_done()调用告诉队列该任务已经处理完毕。

如果当前一个join()正在阻塞,它将在队列中的所有任务都处理完时恢复执行(即每一个由put()调用入队的任务都有一个对应的task_done()调用)。

join()

阻塞调用线程,直到队列中的所有任务被处理掉。

只要有数据被加入队列,未完成的任务数就会增加。当消费者线程调用task_done()(意味着有消费者取得任务并完成任务),未完成的任务数就会减少。当未完成的任务数降到0,join()解除阻塞。

put(item[, block[, timeout]])

将item放入队列中。

  1. 如果可选的参数block为True且timeout为空对象(默认的情况,阻塞调用,无超时)。
  2. 如果timeout是个正整数,阻塞调用进程最多timeout秒,如果一直无空空间可用,抛出Full异常(带超时的阻塞调用)。
  3. 如果block为False,如果有空闲空间可用将数据放入队列,否则立即抛出Full异常

其非阻塞版本为put_nowait等同于put(item, False)

get([block[, timeout]])

从队列中移除并返回一个数据。block跟timeout参数同put方法

其非阻塞方法为`get_nowait()`相当与get(False)

empty()

如果队列为空,返回True,反之返回False

==================================================================================================

创建一个“队列”对象

import Queue
myqueue = Queue.Queue(maxsize = 10)

Queue.Queue类即是一个队列的同步实现。队列长度可为无限或者有限。可通过Queue的构造函数的可选参数maxsize来设定队列长度。如果maxsize小于1就表示队列长度无限。

将一个值放入队列中

myqueue.put(10)

调用队列对象的put()方法在队尾插入一个项目。put()有两个参数,第一个item为必需的,为插入项目的值;第二个block为可选参数,默认为1。如果队列当前为空且block为1,put()方法就使调用线程暂停,直到空出一个数据单元。如果block为0,put方法将引发Full异常。

PS:block参数为True,相当于队伍排满了,就在旁边等着,腾出位置再插进去;block为False,相当于队伍排满了,没位置了,直接投诉,不他妈跟你墨迹

将一个值从队列中取出

myqueue.get()

调用队列对象的get()方法从队头删除并返回一个项目。可选参数为block,默认为True。如果队列为空且block为True,get()就使调用线程暂停,直至有项目可用。如果队列为空且block为False,队列将引发Empty异常。

PS:block参数为True,相当于锅里没吃的了,就在旁边等着上新菜,上了新菜再直接端走;block为False,相当于锅里没货了,没耐心等新菜上锅,直接掀锅砸灶,去你妈的

python queue模块有三种队列:
1、python queue模块的FIFO队列先进先出。
2、LIFO类似于堆。即先进后出。
3、还有一种是优先级队列级别越低越先出来。

针对这三种队列分别有三个构造函数:
1、class Queue.Queue(maxsize) FIFO 
2、class Queue.LifoQueue(maxsize) LIFO 
3、class Queue.PriorityQueue(maxsize) 优先级队列

介绍一下此包中的常用方法:

Queue.qsize() 返回队列的大小 
Queue.empty() 如果队列为空,返回True,反之False 
Queue.full() 如果队列满了,返回True,反之False
Queue.full 与 maxsize 大小对应 
Queue.get([block[, timeout]])获取队列,timeout等待时间 
Queue.get_nowait() 相当Queue.get(False)
非阻塞 Queue.put(item) 写入队列,timeout等待时间 
Queue.put_nowait(item) 相当Queue.put(item, False)
Queue.task_done() 在完成一项工作之后,Queue.task_done()函数向任务已经完成的队列发送一个信号
Queue.join() 实际上意味着等到队列为空,再执行别的操作

一些需要注意的地方:

1. 阻塞模式

import Queue

q = Queue.Queue(10)

......
       for i in range(10):
               q.put('A')
               time.sleep(0.5)

这是一段极其简单的代码(另有两个线程也在操作队列q),我期望每隔0.5秒写一个'A'到队列中,但总是不能如愿:间隔时间有时会远远超过0.5秒。原来,Queue.put()默认有 block = True 和 timeou 两个参数。当  block = True 时,写入是阻塞式的,阻塞时间由 timeou  确定。当队列q被(其他线程)写满后,这段代码就会阻塞,直至其他线程取走数据。Queue.put()方法加上 block=False 的参数,即可解决这个隐蔽的问题。但要注意,非阻塞方式写队列,当队列满时会抛出 exception Queue.Full 的异常。

PS:如果没能及时put,说明队伍满了,还他妈在排队呢,且等着

2. 无法捕获 exception Queue.Empty 的异常

while True:
                ......
                try:
                        data = q.get()
                except Queue.Empty:
                        break

我的本意是用队列为空时,退出循环,但实际运行起来,却陷入了死循环。这个问题和上面有点类似:Queue.get()默认的也是阻塞方式读取数据,队列为空时,不会抛出 except Queue.Empty ,而是进入阻塞直至超时。 加上block=False 的参数,问题迎刃而解。

PS:老子还在排队等上菜,你抛锤子的异常,有本事直接砸锅掀灶台,否则乖乖一边站着等

(转)有关Queue队列的更多相关文章

  1. C#基础---Queue(队列)的应用

       Queue队列,特性先进先出. 在一些项目中我们会遇到对一些数据的Check,如果数据不符合条件将会把不通过的信息返回到界面.但是对于有的数据可能会Check很多条件,如果一个数据一旦很多条件不 ...

  2. 第19章 queue队列容器

    /* 第19章 queue队列容器 19.1 queue技术原理 19.2 queue应用基础 19.3 本章小结 */ // 第19章 queue队列容器 // 19.1 queue技术原理 // ...

  3. atitit. java queue 队列体系and自定义基于数据库的队列总结o7t

    atitit. java queue 队列体系and自定义基于数据库的队列总结o7t 1. 阻塞队列和非阻塞队列 1 2. java.util.Queue接口, 1 3. ConcurrentLink ...

  4. C#部分---特殊集合:stack栈集合、queue队列集合、哈希表集合。

    1.stack栈集合:又名 干草堆集合 栈集合 特点:(1)一个一个赋值 一个一个取值(2)先进后出实例化 初始化 Stack st = new Stack(); //添加元素用push st.Pus ...

  5. 实现一个线程安全的Queue队列

    使用装饰者模式实现一个线程安全的Queue队列. public class SynchronizedQueue<E> implements Queue<E>, Serializ ...

  6. Python自动化运维之16、线程、进程、协程、queue队列

    一.线程 1.什么是线程 线程是操作系统能够进行运算调度的最小单位.它被包含在进程之中,是进程中的实际运作单位. 一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行 ...

  7. Stack集合 Queue队列集合 Hashtable哈希表

    Stack集合 干草堆集合 栈集合 栈;stack,先进后出,一个一个赋值,一个一个取值,安装顺序来. 属性和方法 实例化 初始化 Stack st = new Stack(); 添加元素 个数 Co ...

  8. Python第十五天 datetime模块 time模块 thread模块 threading模块 Queue队列模块 multiprocessing模块 paramiko模块 fabric模块

    Python第十五天  datetime模块 time模块   thread模块  threading模块  Queue队列模块  multiprocessing模块  paramiko模块  fab ...

  9. python threading模块使用 以及python多线程操作的实践(使用Queue队列模块)

    今天花了近乎一天的时间研究python关于多线程的问题,查看了大量源码 自己也实践了一个生产消费者模型,所以把一天的收获总结一下. 由于GIL(Global Interpreter Lock)锁的关系 ...

  10. (8)进程---Queue队列

    # IPC Inter-Process Communication # 实现进程之间通信的两种机制: # 管道 Pipe 用的很少 # 队列 Queue 队列的特征:现进先出,栈属于后进后出 基本语法 ...

随机推荐

  1. 基于swiper的移动端H5页面,丰富的动画效果

    概述 通过运用swiper插件,制作移动端上下整屏滑动的H5页面,用来宣传或者简单注册等,可以嵌套H5音乐或者视频. 详细 代码下载:http://www.demodashi.com/demo/119 ...

  2. [Linux]--解决虚拟机中安装ubuntu不能自适应的问题

    这几天换了新的电脑,但是装上ubuntu mate以后就一直不能自适应窗口大小改变分辨率,奈何我是个强迫症,再加上也不想老师带着自己的笔记本跑动跑西的(主要是太重了...),于是今天花了一下午的时间找 ...

  3. Tomcat中部署Java Web应用程序的方式

    Tomcat中部署Java Web应用程序的几种方式: #PetWeb是工程名 1.在TOMCAT_HOME\conf\server.xml文件的HOST节点中加入 <Context docBa ...

  4. 使用zlib模块实现HTTP服务端与客户端实现传输数据压缩

    现如今在处理http请求的时候,由于请求的资源较多,如果不启用压缩的话,那么页面请求的流量将会非常大.启用gzip压缩,在一定程度上会大大的提高页面性能. 因此这写一个使用Node.js实现在http ...

  5. zeroclipboard解决跨域问题

    ZeroClipboard.setDefaults({ moviePath: "//d2glos6gx2bw40.cloudfront.net/C8QpR9/images/flash/Zer ...

  6. ubuntu中rc.local无效

    在ubuntu中写了一点iptables规则,但是,竟然iptables竟然无效,经过多方查找问题...眼泪... 终于发现是rc.local竟然没有运行,我晕.仔细检查iptables脚本n遍,没有 ...

  7. [elk]elk的诸多beats&&kibana插件

    elk的诸多beats 参考: https://www.elastic.co/guide/en/beats/libbeat/current/community-beats.html jmxproxyb ...

  8. 2014 Multi-University Training Contest 1/HDU4864_Task(贪心)

    解题报告 题意,有n个机器.m个任务. 每一个机器至多能完毕一个任务.对于每一个机器,有一个最大执行时间Ti和等级Li,对于每一个任务,也有一个执行时间Tj和等级Lj.仅仅有当Ti>=Tj且Li ...

  9. Phonegap创建项目语法

    1:在本地磁盘新建一个文件夹存放要开发的项目,比如在D盘建一个yun文件夹2 2:然后在dos系统下,d:命令进入d盘,cd yun进入yun文件夹, 3:然后phonegap create yun2 ...

  10. 【C语言】23-typedef

    一.typedef作用简介 * 我们可以使用typedef关键字为各种数据类型定义一个新名字(别名). 1 #include <stdio.h> 2 3 typedef int Integ ...