阻塞队列和生产消费模型

news2025/1/4 19:00:58

阻塞队列

阻塞队列的概念

队列相信我们已经不陌生了 之前也学过很多队列 比如: 普通队列优先级队列 两种
这两种队列都是线程不安全的
而我们讲的阻塞队列 刚好可以解决线程安全问题 也是先进先出 并且带有阻塞功能.
阻塞功能是怎么回事呢

就是如果入队的时候阻塞队列为满 ,则当前线程就会进入阻塞状态,阻塞到有出队列操作才会再唤醒线程继续执行 ,相同 如果出队时阻塞队列为空,则当前线程也会进入阻塞状态 直到有新元素入队操作才会唤醒继续执行该线程.

在Java标准库中,BlockingQueue这个就是标准库提供的阻塞队列. 阻塞队列在实际开发中使用的场景十分广泛. 在阻塞方法中 有独特的进队列和出队列的方法 其他一些普通的方法阻塞队列也有 ,但是使用阻塞队列一般都不会再使用普通队列的方法了.

消息队列

消息队列这种数据结构其实也是阻塞队列的一种 ,也带有阻塞特性.它不是普通的先进先出,而是通过topic这样的参数来对数据进行分类,出队列的时候,指定topic,每个topic下的数据是先进先出. 消息队列只要应用于生产者消费者模型.

生产者消费者模型

什么是生产者和消费者模型呢 ?
举个例子:
就相当于两个人制作饺子 要分为两步 一步是擀饺子皮 一步是包饺子. 要两个人分工合作,实际上 要包饺子就得先擀饺子皮 那擀饺子皮的人相当于生产者 包饺子皮的人就相当于消费者 擀好的饺子皮要用一个容器来盛放 ,而这个容器就相当于阻塞队列/消息队列. 有了这个容器就会有阻塞功能 ,现在A擀饺子皮 B包饺子 如果B包饺子包得快 A擀饺子皮慢 那容器里面的饺子皮很快就会空了 这时候B就要阻塞等待A擀饺子皮 每擀一个就包一个饺子 ,相反 如果A擀饺子皮擀得比较快 B包饺子慢,那么容器很快就会满了,这样A就会阻塞等待 B包饺子 B每包一个 A就擀一个.

在这里插入图片描述
上面图片就是生产者和消费者模型

你们想一想 在实际开发中为什么要用到这个生产者消费者模型 ? 相当于在开发中 有两种服务器 :请求服务器Q和应用服务器Y 如果QY直接传递消息 ,没有阻塞队列的情况下,如果Q突然请求有很多的时候,Y的请求也就会跟着暴涨 ,但Y服务器是应用服务器,他处理任务的过程很复杂 是重量级的 这样就会让Y服务器直接G.

这时我们如果我们引入生产者消费者模型,这样即使Q服务器的请求再怎么多,也不会影响到Y服务器 最坏的情况也就是Q服务器挂了 但Y服务器不会有任何影响 因为Q的请求都会放在阻塞队列中 , 有界 的阻塞队列就会引起阻塞 Y服务器 还是和原来一样处理这些请求 这样就起到了"削峰填谷"的作用.
这个模型还有一个优势就是高内聚低耦合 两个服务器不会直接接触 一个挂了不会对另一个产生影响.

用循环队列实现一个简单的阻塞队列 用于实现一个生产者消费者模型

第一种 就是生产者生产快 而消费者慢 就会出现 程序一运行生产者咔咔就会生产满了 接下来就会阻塞 消防者每消费一个 生产者才会生产一个. 下面我们通过代码来实现一下:

class MyBlockingQueue{
    private String[] elems = null;
    private volatile int head = 0;
    private volatile int tail = 0;
    private volatile int size = 0;

    public MyBlockingQueue(int capacity) {
        elems = new String[capacity];
    }

    void put(String elem) throws InterruptedException {
        //先加锁
        synchronized (this) {
            while (size >= elems.length) {
                //队列满了 ,就要等待
                this.wait();
            }

            //把新的元素放到tail所在的位置上
            elems[tail] = elem;
            tail++;
            if (tail >= elems.length) {
                //到达末尾  ,就回到开头
                tail = 0;
            }
            //更新size的值
            size++;
            //唤醒下面take的wait
            this.notify();
        }
    }

    String take() throws InterruptedException {
        synchronized (this) {
            while (size == 0) {
                //为空要等待
                this.wait();
            }
            //取出 head指向的元素
            String result = elems[head];
            head++;
            if (head >= elems.length) {
                head = 0;
            }

            size--;
            //唤醒put上面的wait
            this.notify();
            return result;
        }

    }
}

public class Text2 {
    //实现一个阻塞队列 模拟一个生产者消费者模型
    public static void main(String[] args) {
        //实例化一个阻塞队列的对象   利用该阻塞队列实现一个生产者消费者模型
        MyBlockingQueue queue = new MyBlockingQueue(1000);

        //生产者线程
        Thread t1 = new Thread(() -> {
            try {
                int count = 0;
                while (true) {
                    queue.put(count + "");
                    System.out.println("生产:" + count);
                    count++;
                }
            }catch (InterruptedException e) {
                e.printStackTrace();
            }
        });

        //消费者线程
        Thread t2 = new Thread(() ->{
            try {
                while (true) {
                    String result = queue.take();
                    System.out.println("消费:" + result );
                    Thread.sleep(1000);
                }
            }catch (InterruptedException e) {
                e.printStackTrace();
            }
        });
        t1.start();
        t2.start();
    }
}

运行截图:
在这里插入图片描述
其实这里生产者和消费者的频率和快慢 我们都是可以通过代码来控制的 .
上面就是阻塞队列的应用场景 .

相信通过上诉内容 大家都了解并掌握阻塞队列了吧!

下一章内容 : 我们就会讲到线程池的有关内容 .

谢谢大家的浏览 !!!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1591533.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

AI的智商如何测试?

一、AI的智商测试 AI的智商测试不同于人类的智商测试,因为它涉及到不同类型的智能和功能衡量标准。以下是几种常见的AI智商测试或评估方式: 此图片来源于网络 1. **功能性测试**: - 对于算法或机器学习模型,可以通过标准化的基…

探秘大模型:《提示工程:技巧、方法与行业应用》背后的故事

提示工程是一种新兴的利用人工智能的技术,它通过设计提示引导生成式 AI 模型产生预期的输出,来提升人与 AI 的互动质量,激发 AI 模型的潜力,提升AI的应用水平。 为了让每一个人都拥有驱动大模型的能力,以微软全球副总裁…

maven之pom中的build标签

1、build标签分类 1.1、全局配置&#xff08;project build&#xff09; 针对整个项目的所有情况都有效。 <project xmlns"http://maven.apache.org/POM/4.0.0" xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation"htt…

Linux执行命令监控详细实现原理和使用教程,以及相关工具的使用

Linux执行命令监控详细实现原理和使用教程&#xff0c;以及相关工具的使用。 0x00 背景介绍 Linux上的HIDS需要实时对执行的命令进行监控&#xff0c;分析异常或入侵行为&#xff0c;有助于安全事件的发现和预防。为了获取执行命令&#xff0c;大致有如下方法&#xff1a; 遍…

OJ 古籍翻译 【进制转化】【C】

这里有两个考察点&#xff0c;一个是进制转换&#xff0c;还有一个是以字符串输出 知识点&#xff1a; sprintf(参数一&#xff0c;参数二&#xff0c;参数三) 将参数三按参数二的格式转换后存入参数一中 sprintf与printf用法基本一样&#xff0c;只是sprintf是将值打印到指…

R语言数据可视化:基本绘图系统

目录 plot函数 par函数 hist函数 boxplot函数 plot函数应用实战 全局参数 R语言中有三大绘图系统包括基本绘图系统&#xff0c;Lattice绘图系统&#xff0c;ggplot2绘图系统 基本绘图系统 在R语言中&#xff0c;以下函数通常用于创建和定制图形&#xff1a; plot 函数…

ansible的常见用法

目录 ##编辑hosts文件 ##copy模块##复制过去 ##fetch模块##拉取 ##shell模块 ##好用 ##command模块## ##file模块### ##cron模块### ##crontab 计划任务 ##下载好时间插件 ##script模块 ##yum模块## ##yum下载源配置文件 /etc/yum.repos.d/CentOS-Base.repo ##ser…

时间序列分析 # 平稳性检验和ARMA模型的识别与定阶 #R语言

掌握单位根检验的原理并能解读结果&#xff1b;掌握利用序列的自相关图和偏自相关图识别模型并进行初步定阶。 原始数据在文末&#xff01;&#xff01;&#xff01; 练习1、根据某1971年9月-1993年6月澳大利亚季度常住人口变动&#xff08;单位&#xff1a;千人&#xff09;的…

MySQL 嵌套查询

嵌套查询 是指在一个完整的查询语句之中&#xff0c;包含若干个不同功能的小查询&#xff1b;从而一起完成复杂查询的一种编写形式。包含的查询放在&#xff08;&#xff09;里 &#xff0c; 包含的查询出现的位置&#xff1a; 位置含义SELECT之后把查询结果作为表头使用FROM…

ubuntu20.04.3挂载共享文件夹

VMware设置win共享文件夹 在linux执行挂载命令 sudo vmhgfs-fuse /mnt/hgfs/ -o nonempty这样就可以用管理员访问/mnt/hgfs/share

场景:如何做数据清理

如果数据清理简单粗暴按时间进行清理&#xff0c;同时时间字段并没有增加索引就会出问题 如果没有增加索引&#xff0c;他就会进行全表扫描&#xff0c;并且会给全表的数据上一个x锁 会阻塞其他的线程 解决方案参考阿里云DMS数据清理方案 这个SQL查询的目的是从名为table_hol…

2024年mathorcup数学建模思路及论文助攻

题目C题 物流网络分拣中心货量预测及人员排班 电商物流网络在订单履约中由多个环节组成&#xff0c;图1是一个简化的物流网络示意图。其中&#xff0c;分拣中心作为网络的中间环节&#xff0c;需要将包裹按照不同流向进行分拣并发往下一个场地&#xff0c;最终使包裹到达消费者…

Towards Street-Level Client-Independent IP Geolocation(2011年)(第一部分)

被引次数:306 Wang Y, Burgener D, Flores M, et al. Towards {Street-Level}{Client-Independent}{IP} Geolocation[C]//8th USENIX Symposium on Networked Systems Design and Implementation (NSDI 11). 2011. Abstract 一个高度精确的客户端独立的地理定位服务将是互联…

电商广告中的OCPC是什么?OCPC原理是什么?

1.定义&#xff1a; OCPC是指optimized cost per click&#xff08;以目标转化为优化方式的点击出价&#xff09;&#xff0c;本质还是按照cpc付费。 2.三大特点&#xff1a;抢流量、避免无效流量、提高转化&#xff1b; 3.放量原理&#xff1a; 通过捕捉用户行为、行业数据…

数组算法——查询位置

需求 思路 使用二分查找找到第一个值&#xff0c;以第一个值作为界限&#xff0c;分为左右两个区间在左右两个区间分别使用二分查找找左边的7,&#xff1a;找到中间位置的7之后&#xff0c;将中间位置的7作为结束位置&#xff0c;依次循环查找&#xff0c;知道start>end,返回…

股票价格预测 | Python使用LSTM预测股票价格

文章目录 效果一览文章概述代码设计效果一览 文章概述 Python使用LSTM预测股票价格 代码设计 import pandas as pd import matplotlib.pyplot as plt import numpy as np import tensorflowfrom numpy import

mui和uniapp跳转外部链接

Hbuilder开发的app&#xff0c;会涉及到跳转H5页面 mui <!DOCTYPE html> <html><head><meta charset"utf-8"><meta name"viewport" content"initial-scale1.0, maximum-scale1.0, user-scalableno" /><link …

明明设置数字居中对齐,为什么excel的数字却不居中?

有时候在excel里&#xff0c;选中数据&#xff0c;设置对齐方式 左右居中&#xff0c;然而&#xff0c;数字却怎么都不居中&#xff0c;为什么呢&#xff1f; 1.按快捷键Ctrl1&#xff0c;打开单元格自定义格式对话框&#xff0c;看到是初始界面是在数字的会计专用&#xff0c;…

浮点数加减运算、强制类型转换

目录 王道考研ppt总结&#xff1a; 二、个人理解 浮点数加减运算步骤&#xff1a;1、对阶2、尾数加减3、规格化&#xff08;左规和右规&#xff09;4、舍入5、判断溢出 三、数据类型转换 王道考研ppt总结&#xff1a; 二、个人理解 浮点数加减运算步骤&#xff1a; 1、对…

Suno AI

Suno is the latest big name in AI, but what is it? Keep reading to learn everything you need to know about Suno AI, including what it is, what it can do, and how much it costs. Suno AI是一款由Anthropic公司开发的人工智能音乐生成器&#xff0c;它利用先进…