python 多线程系列—condition 对象 (四)

一、条件对象condition

1、threading.Condition 条件对象 用于线程之间的通信。条件变量总是与某种类型的锁对象(Lock/RLock)相关联,锁对象可以通过参数传入或默认自动创建。条件对象的方法必须要在线程持有关联锁的情况下才能调用。
2、调用 wait() 方法会阻塞线程并释放锁,然后直到超时或被其他线程调用 notify() 或 notify_all() 方法唤醒,一旦被唤醒,wait() 方法将重新请求获取到锁后才能返回。
3、notify() 和 notify_all() 方法并不会释放锁,因此被唤醒的线程不会立即从 wait() 方法返回,而是等其他线程释放锁后,调用 wait() 的线程重新竞争获得锁后才能继续。

二、Conditions对象使用

场景:模拟狗吃骨头的场景
1、生产者类:在骨头少于10根的时候开始生产骨头
2、消费者类:在骨头大于0的时候开始吃骨头

三、代码

import random
import threading
from threading import Condition

class Produce(threading.Thread):
    def __init__(self,con:Condition,bone_list:list):
        super().__init__()
        self.con = con
        self.bone_list = bone_list
    def run(self) -> None:
        #获取锁
        self.con.acquire()
        while True:
            #判断骨头是都少于10块,大于10块就等待,不生成骨头
            if len(self.bone_list)>10:
                # 阻塞,python解释器释放锁
                # 线程锁释放的两种情况:等待(IO)导致python解释器锁释放,线程执行时长达到指定的阈值0.005秒
                self.con.wait()
            else:
                self.bone_list.append(random.randint(1,10000))
                print("骨头列表:", self.bone_list)
                #唤醒处于等待状态的线程
                self.con.notify()

class Consumer(threading.Thread):
    def __init__(self,con:Condition,bone_list:list):
        super().__init__()
        self.con = con
        self.bone_list = bone_list

    def run(self) -> None:
        #获取锁
        self.con.acquire()
        while True:
            #判断骨头是都少于10块,大于10块就等待,不生成骨头
            if len(self.bone_list)<1:
                # 阻塞,python解释器释放锁
                # 线程锁释放的两种情况:等待(IO)导致python解释器锁释放,线程执行时长达到指定的阈值0.005秒
                self.con.wait()
            else:
                #删除最先进去的元素
                result = self.bone_list.pop(0)
                print(f"大黄{self.name}在吃骨头",result)
                print("消费者-骨头列表:",self.bone_list)
                #唤醒处于等待状态的线程
                self.con.notify()

def done():
    con = threading.Condition()
    bone_list = []
    #创建生产者
    produce = Produce(con=con,bone_list=bone_list)
    produce.start()
    #创建多个消费者
    for i in range(10):
        consumer = Consumer(con=con,bone_list=bone_list)
        consumer.start()
done()
1 操作
haili 在 2022-08-04 19:22:58 更新了该帖
回帖
请输入回帖内容 ...