• python多线程编程(6): 队列同步


    原文请看:http://www.cnblogs.com/holbrook/archive/2012/03/15/2398060.html

    前面介绍了互斥锁条件变量解决线程间的同步问题,并使用条件变量同步机制解决了生产者与消费者问题

    让我们考虑更复杂的一种场景:产品是各不相同的。这时只记录一个数量就不够了,还需要记录每个产品的细节。很容易想到需要用一个容器将这些产品记录下来。

    Python的Queue模块中提供了同步的、线程安全的队列类,包括FIFO(先入先出)队列Queue,LIFO(后入先出)队列 LifoQueue,和优先级队列PriorityQueue。这些队列都实现了锁原语,能够在多线程中直接使用。可以使用队列来实现线程间的同步。

    用FIFO队列实现上述生产者与消费者问题的代码如下:

     1 #encoding=utf-8
     2 import threading
     3 import time
     4 from Queue import Queue
     5 
     6 class Producer(threading.Thread):
     7     def run(self):
     8         global queue
     9         count = 0
    10         while True:
    11             for i in range(100):
    12                 if queue.qsize() > 1000:
    13                      pass
    14                 else:
    15                      count = count +1
    16                      msg = '生成产品'+str(count)
    17                      queue.put(msg)
    18                      print msg
    19             time.sleep(1)
    20 
    21 class Consumer(threading.Thread):
    22     def run(self):
    23         global queue
    24         while True:
    25             for i in range(3):
    26                 if queue.qsize() < 100:
    27                     pass
    28                 else:
    29                     msg = self.name + '消费了 '+queue.get()
    30                     print msg
    31             time.sleep(1)
    32 
    33 queue = Queue()
    34 
    35 
    36 def test():
    37     for i in range(500):
    38         queue.put('初始产品'+str(i))
    39     for i in range(2):
    40         p = Producer()
    41         p.start()
    42     for i in range(5):
    43         c = Consumer()
    44         c.start()
    45 if __name__ == '__main__':
    46     test()

     一点说明

    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异常。

    将一个值从队列中取出

    myqueue.get()

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


    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() 实际上意味着等到队列为空,再执行别的操作
  • 相关阅读:
    react路由传参的三种方式:
    毕设登录逻辑分析
    redis缓存数据库的配置和分析
    c#窗体虚线图形验证码设计
    C#窗体技巧
    关于子窗体的层级关系
    安装SQL SERVER开启SA用户登录的方法
    SQL中CONVERT日期不同格式的转换用法
    sql server中自连接的使用
    IFieldEdit Interface 接口
  • 原文地址:https://www.cnblogs.com/mmix2009/p/3223109.html
Copyright © 2020-2023  润新知