threading多线程的生产者消费者模型

理解此篇请先看http://www.cnblogs.com/haiyan123/p/7445584.html

"""多线程下生产者消费者模型。定义:在同一进程,同一主线程下,
采用多线程完成多个任务的同时,各自数据保持干净整洁。即、花最少的时间
完成最多的任务"""
import threading
import random
import time
# 初始化金额
gMoney = 1000
#
gLock = threading.Lock()
# 最大生产次数
gTotalTimes = 10
# 计数器
gTimes = 0


class Producer(threading.Thread):
    """生产者"""
    def run(self):
        global gMoney      # 引用全局变量需先声明
        global gTimes
        while True:
            # 生产随机金额
            money = random.randint(100, 1000)
            # 加锁
            gLock.acquire()
            # 判断生产次数
            if gTimes >= gTotalTimes:
                gLock.release()
                break
            # 金额增加
            gMoney += money
            print("%s生产了%d元钱,剩余%d元钱" % ("小黑", money, gMoney))
            # 生产完成计数器加一
            gTimes += 1
            # 释放锁
            gLock.release()
            time.sleep(1)


class Consumer(threading.Thread):
    """消费者"""
    def run(self):
        global gMoney
        while True:
            # 消费随机金额
            money = random.randint(100, 1000)
            # 加锁
            gLock.acquire()
            # 判断剩余金额大于消费数继续消费
            if gMoney >= money:
                gMoney -= money
                print("%s消费了%d元钱,剩余%d元钱" % ("小胖子", money, gMoney))
            else:
                # 判断生产次数大于最大生产数停止消费释放锁
                if gTimes >= gTotalTimes:
                    gLock.release()
                    break
                print("%s消费者准备消费%d元钱,剩余%d元钱,不足" % ("小白", money, gMoney))
            # 释放锁
            gLock.release()
            time.sleep(1)


def main():
    for x in range(5):
        t = Producer(name="生产者线程%s" % x)
        t.start()

    for i in range(3):
        t = Consumer(name="消费者线程%s" % i)
        t.start()


if __name__ == '__main__':
    main()
View Code

 线程执行效率优化之condition

"""confition采用事件通知,避免while True:条件下空数据后反复循环。"""
import threading
import random
import time
# 初始化金额
gMoney = 1000
#
gCondition = threading.Condition()    #
# 最大生产次数
gTotalTimes = 10
# 计数器
gTimes = 0


class Producer(threading.Thread):
    """生产者"""
    def run(self):
        global gMoney      # 引用全局变量需先声明
        global gTimes
        while True:
            # 生产随机金额
            money = random.randint(100, 1000)
            # 加锁
            gCondition.acquire()
            # 判断生产次数
            if gTimes >= gTotalTimes:
                gCondition.release()
                break
            # 金额增加
            gMoney += money
            print("%s生产了%d元钱,剩余%d元钱" % ("小黑", money, gMoney))
            # 生产完成计数器加一
            gTimes += 1
            # 通知所有正在等待的线程
            gCondition.notify_all()
            # 释放锁
            gCondition.release()
            time.sleep(1)


class Consumer(threading.Thread):
    """消费者"""
    def run(self):
        global gMoney
        while True:
            # 消费随机金额
            money = random.randint(100, 1000)
            # 加锁
            gCondition.acquire()
            while gMoney < money:
                if gTimes >= gTotalTimes:
                    gCondition.release()
                    return
                print("%s准备消费%d元钱,剩余%d元钱,不足" % ("小胖子", money, gMoney))
                # 钱不够就夯住,不会去反复上锁解锁,等待被唤醒
                gCondition.wait()
            gMoney -= money
            print("%s消费了%d元钱,剩余%d元钱" % ("小胖子", money, gMoney))
            gCondition.release()
            time.sleep(1)


def main():
    for i in range(3):
        t = Consumer(name="消费者线程%s" % i)
        t.start()

    for x in range(5):
        t = Producer(name="生产者线程%s" % x)
        t.start()


if __name__ == '__main__':
    main()
View Code

 线程安全队列之queue

"""queue线程安全队列,先进先出"""
from queue import Queue
import threading
import time

q = Queue(2)    # 生成q队列对象,参数表示最大队列数(限制用)
q.put(1)        # 推送值到q队列中
q.put(2)
print(q.qsize())          # 获取队列中队列个数
print(q.full())           # 判断队列是否满了,满为True,反之False
print(q.empty())          # 队列为空返回True,反之False
print(q.get())            # 从q队列中获取值
# block=True默认
q.get(block=True)         # 获取不到值默认夯住
q.put(1)                   # 满了默认夯住


def set_value(q):
    index = 0
    while True:
        q.put(index)
        index += 1
        time.sleep(3)


def get_value(q):
    while True:
        print(q.get())


def main():
    q = Queue(4)
    # 传递q给调用函数
    t1 = threading.Thread(target=set_value, args=[q])
    t2 = threading.Thread(target=get_value, args=[q])
    t1.start()
    t2.start()


if __name__ == '__main__':
    main()
View Code

 

posted @ 2018-10-24 17:54  知你几分  阅读(333)  评论(0编辑  收藏  举报