condition版生产者与消费者模式
1.简介
在爬虫中,生产者与消费者模式是经常用到的。我能想到的比较好的办法是使用redis或者mongodb数据库构造生产者消费者模型。如果直接起线程进行构造生产者消费者模型,线程容易假死,也难以构造复杂的生产者消费者模型。这里提供的condition版其实是最基本的生产者消费者模型的改良版,为了保护数据安全依旧是要开锁进行操作,但是不会循环的一直开锁,而是一旦条件不符合,则会阻塞,直到符合运行程序的条件。但是还是太low,不过这种思路值得借鉴。
2.代码
# -*-coding:utf8 -*- import threading # Lock版本的生产者消费者模式可以正常的运行,但是太消耗CPU资源。
# 使用while循环的方式一直开锁解锁,很消耗资源。threading.Condition可以看作Lock的改良版
# 还有一个更好的模式就是用threading.Condition来实现
# threading.Condition可以在没有数据的时候处于阻塞等待状态,一旦有合适的数据了,
# 还可以使用notify相关的函数来通知其他处于等待状态的线程。这样就可以不用做一些无用的上锁
# 和解锁的操作,可以提高程序的性能。 # 1.acquire:获取锁
# 2.release:解锁
# 3.wait:释放内部占用的锁,同时线程被挂起。可以被其他线程用notify和notify_all函数唤醒,
# 被唤醒后会继续等待获取锁,获取锁后继续执行下面的代码
# 4.notify:唤醒一个挂起的线程,默认是第一个等待的线程。注意:notify不会释放所占用的锁
# 5.notify_all:通知所有正在等待的线程。notify和notify_all不会释放锁。并且需要在release之前调用 # -*-coding:utf8 -*-
import threading
import random
import time gMoney = 1000
gCondition = threading.Condition()
gTimes = 0
gTotalTimes = 30 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
gTimes += 1
print('%s生产了%s元钱,剩余%s元钱' % (threading.current_thread(), money, gMoney))
gCondition.notify_all()
gCondition.release()
time.sleep(0.5) 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
# 当不满足条件时,直接进入阻塞,不在循环开锁,关锁的消耗资源的操作
gCondition.wait()
gMoney -= money
print('%s消费了%d元钱,剩余%d元钱' % (threading.current_thread(), money, gMoney))
gCondition.release()
time.sleep(0.5) def main():
for x in range(5):
t = Consumer(name='消费者线程%s' % x)
t.start()
for x in range(2):
t = Producer(name='生产者线程%s' % x)
t.start() if __name__ == '__main__':
main()
condition版生产者与消费者模式的更多相关文章
- 用ReentrantLock和Condition实现生产者和消费者模式
前面一篇文章<wait.notify应用场景(生产者-消费者模式)>是一种生产者消费者模式实现,今晚这是Lock方式实现,下面是源码: 生产者代码: /** * 生产者 * * @auth ...
- 【爬虫】Condition版的生产者和消费者模式
Condition版的生产者和消费者模式 threading.Condition 在没有数据的时候处于阻塞状态,有数据可以使用notify的函数通知等等待状态的线程运作 threading.Condi ...
- 【爬虫】Load版的生产者和消费者模式
''' Lock版的生产者和消费者模式 ''' import threading import random import time gMoney = 1000 # 原始金额 gLoad = thre ...
- Java并发编程(4)--生产者与消费者模式介绍
一.前言 这种模式在生活是最常见的,那么它的场景是什么样的呢? 下面是我假象的,假设有一个仓库,仓库有一个生产者和一个消费者,消费者过来消费的时候会检测仓库中是否有库存,如果没有了则等待生产,如果有就 ...
- 使用libuv实现生产者和消费者模式
生产者和消费者模式(Consumer + Producer model) 用于把耗时操作(生产线程),分配给一个或者多个额外线程执行(消费线程),从而提高生产线程的响应速度(并发能力) 定义 type ...
- java生产者与消费者模式
前言: 生产者和消费者模式是我们在学习多线程中很经典的一个模式,它主要分为生产者和消费者,分别是两个线程, 目录 一:生产者和消费者模式简介 二:生产者和消费者模式的实现 声明:本例来源于java经典 ...
- Java多线程设计模式(2)生产者与消费者模式
1 Producer-Consumer Pattern Producer-Consumer Pattern主要就是在生产者与消费者之间建立一个“桥梁参与者”,用来解决生产者线程与消费者线程之间速度的不 ...
- java 线程并发(生产者、消费者模式)
线程并发协作(生产者/消费者模式) 多线程环境下,我们经常需要多个线程的并发和协作.这个时候,就需要了解一个重要的多线程并发协作模型“生产者/消费者模式”. Ø 什么是生产者? 生产者指的是负责生产数 ...
- java进阶(40)--wait与notify(生产者与消费者模式)
文档目录: 一.概念 二.wait的作用 三.notify的作用 四.生产者消费者模式 五.举例 ---------------------------------------分割线:正文------ ...
随机推荐
- 怎么给PDF文件交换页面
在使用PDF文件的时候有文件页面的排版错误的时候,这个时候就需要交换页面了,那么怎么给PDF文件交换页面呢,在使用PDF文件的时候需要交换页面的时候要怎么做呢,下面小编就为大家分享一下PDF文件交换页 ...
- spring官网上下载历史版本的spring插件,springsource-tool-suite
spring官网下载地址(https://spring.io/tools/sts/all),历史版本地址(https://spring.io/tools/sts/legacy). 注:历史版本下载的都 ...
- using 关键字的作用
我们都知道可以使用using关键字引入命名空间,例如:using namespace std; using还有个作用是在子类中引入父类成员函数. 1) 当子类没有定义和父类同名的函数(virtual也 ...
- sqlserver 脚本生成数据库文档
SELECT ( then d.name else '' end)表名, --a.colorder 字段序号, a.name 字段名, --(case ...
- 课堂小记---JavaScript(1)
day01 1.数据类型 number string boolean undefined object function 加号具有两种功能,数字相加 和 字符串拼接.加号两边只要碰见字符串,则执行字 ...
- 关于H5页面在iPhoneX适配
1. iPhoneX的介绍 屏幕尺寸 我们熟知的iPhone系列开发尺寸概要如下: △ iPhone各机型的开发尺寸 转化成我们熟知的像素尺寸: △ 每个机型的多维度尺寸 倍图其实就是像素尺寸和开 ...
- Android项目中的config.xml文件 “config.xml”
Android应用程序需要保存一些配置时,可以将这些配置项放置到values/config.xml文件中. 实例分析: <?xml version="1.0" encodin ...
- Matrix [POJ3685] [二分套二分]
Description 有一个N阶方阵 第i行,j列的值Aij =i2 + 100000 × i + j2 - 100000 × j + i × j,需要找出这个方阵的第M小值. Input 第一行输 ...
- C#超简单自定义事件
我知道你为啥点进来,所以不要犹豫了,立刻马上果断创建控制台项目,直接复制下面精干短小而又强大的代码运行: using System; using System.Collections.Generic; ...
- IDEA_教你十分钟下载并破解IntelliJ IDEA(2017)(转)
之前都是用myeclipse,但是最近发现看的很多教学视频都是使用 IntelliJ IDEA,于是决定换个软件开始新的学习征程! 下面讲讲我是如何在十分钟之内安装并破解该软件. 1.首先,我找到了 ...