java学习-阻塞队列原理

news2024/11/16 3:33:54

JAVA 阻塞队列原理

阻塞队列,关键字是阻塞,先理解阻塞的含义,在阻塞队列中,线程阻塞有这样的两种情况:

  1. 当队列中没有数据的情况下,消费者端的所有线程都会被自动阻塞(挂起),直到有数据放
    入队列。
  2. 当队列中填满数据的情况下,生产者端的所有线程都会被自动阻塞(挂起),直到队列中有
    空的位置,线程被自动唤醒。

1. 阻塞队列的主要方法

„ 抛出异常:抛出一个异常;
„ 特殊值:返回一个特殊值(null 或 false,视情况而定)
„ 则塞:在成功操作之前,一直阻塞线程
„ 超时:放弃前只在最大的时间内阻塞
在这里插入图片描述

插入操作:

1:public abstract boolean add(E paramE):将指定元素插入此队列中(如果立即可行
且不会违反容量限制),成功时返回 true,如果当前没有可用的空间,则抛
出 IllegalStateException。如果该元素是 NULL,则会抛出 NullPointerException 异常。
2:public abstract boolean offer(E paramE):将指定元素插入此队列中(如果立即可行
且不会违反容量限制),成功时返回 true,如果当前没有可用的空间,则返回 false。
3:public abstract void put(E paramE) throws InterruptedException: 将指定元素插
入此队列中,将等待可用的空间(如果有必要)

public void put(E paramE) throws InterruptedException {
checkNotNull(paramE);
ReentrantLock localReentrantLock = this.lock;
localReentrantLock.lockInterruptibly();
try {
while (this.count == this.items.length)
this.notFull.await();//如果队列满了,则线程阻塞等待
enqueue(paramE);

localReentrantLock.unlock();
} finally {
localReentrantLock.unlock();
}
}

4:offer(E o, long timeout, TimeUnit unit):可以设定等待的时间,如果在指定的时间
内,还不能往队列中加入 BlockingQueue,则返回失败。

获取数据操作:

1:poll(time):取走 BlockingQueue 里排在首位的对象,若不能立即取出,则可以等 time 参数
规定的时间,取不到时返回 null;
2:poll(long timeout, TimeUnit unit):从 BlockingQueue 取出一个队首的对象,如果在
指定时间内,队列一旦有数据可取,则立即返回队列中的数据。否则直到时间超时还没有数
据可取,返回失败。
3:take():取走 BlockingQueue 里排在首位的对象,若 BlockingQueue 为空,阻断进入等待状
态直到 BlockingQueue 有新的数据被加入。
4.drainTo():一次性从 BlockingQueue 获取所有可用的数据对象(还可以指定获取数据的个
数),通过该方法,可以提升获取数据效率;不需要多次分批加锁或释放锁。

2. Java 中的阻塞队列

  1. ArrayBlockingQueue :由数组结构组成的有界阻塞队列。
  2. LinkedBlockingQueue :由链表结构组成的有界阻塞队列。
  3. PriorityBlockingQueue :支持优先级排序的无界阻塞队列。
  4. DelayQueue:使用优先级队列实现的无界阻塞队列。
  5. SynchronousQueue:不存储元素的阻塞队列。
  6. LinkedTransferQueue:由链表结构组成的无界阻塞队列。
  7. LinkedBlockingDeque:由链表结构组成的双向阻塞队列
    在这里插入图片描述

.3. ArrayBlockingQueue(公平、非公平)

用数组实现的有界阻塞队列。此队列按照先进先出(FIFO)的原则对元素进行排序。默认情况下
不保证访问者公平的访问队列,所谓公平访问队列是指阻塞的所有生产者线程或消费者线程,当
队列可用时,可以按照阻塞的先后顺序访问队列,即先阻塞的生产者线程,可以先往队列里插入
元素,先阻塞的消费者线程,可以先从队列里获取元素。通常情况下为了保证公平性会降低吞吐
量。我们可以使用以下代码创建一个公平的阻塞队列:
ArrayBlockingQueue fairQueue = new ArrayBlockingQueue(1000,true);

4. LinkedBlockingQueue(两个独立锁提高并发)

基于链表的阻塞队列,同 ArrayListBlockingQueue 类似,此队列按照先进先出(FIFO)的原则对
元素进行排序。而 LinkedBlockingQueue 之所以能够高效的处理并发数据,还因为其对于生产者
端和消费者端分别采用了独立的锁来控制数据同步,这也意味着在高并发的情况下生产者和消费
者可以并行地操作队列中的数据,以此来提高整个队列的并发性能。
LinkedBlockingQueue 会默认一个类似无限大小的容量(Integer.MAX_VALUE)。

5. PriorityBlockingQueue(compareTo 排序实现优先)

是 一 个支持优先级的无界队列 。默认情况下元素采取自然顺序升序排列。 可以自定义实现
compareTo()方法来指定元素进行排序规则,或者初始化 PriorityBlockingQueue 时,指定构造
参数 Comparator 来对元素进行排序。需要注意的是不能保证同优先级元素的顺序。

6. DelayQueue(缓存失效、定时任务 )

是一个支持延时获取元素的无界阻塞队列。队列使用 PriorityQueue 来实现。队列中的元素必须实
现 Delayed 接口,在创建元素时可以指定多久才能从队列中获取当前元素。只有在延迟期满时才
能从队列中提取元素。我们可以将 DelayQueue 运用在以下应用场景:

  1. 缓存系统的设计:可以用 DelayQueue 保存缓存元素的有效期,使用一个线程循环查询
    DelayQueue,一旦能从 DelayQueue 中获取元素时,表示缓存有效期到了。

  2. 定 时 任 务 调 度 : 使 用 DelayQueue 保 存 当 天 将 会 执 行 的 任 务 和 执 行 时 间 , 一 旦 从
    DelayQueue 中获取到任务就开始执行,从比如 TimerQueue 就是使用 DelayQueue 实现的。

7. SynchronousQueue(不存储数据、可用于传递数据)

是一个不存储元素的阻塞队列。每一个 put 操作必须等待一个 take 操作,否则不能继续添加元素。
SynchronousQueue 可以看成是一个传球手,负责把生产者线程处理的数据直接传递给消费者线
程。队列本身并不存储任何元素,非常适合于传递性场景,比如在一个线程中使用的数据,传递给
另 外 一 个 线 程 使 用 , SynchronousQueue 的 吞 吐 量 高 于 LinkedBlockingQueue 和
ArrayBlockingQueue。

8. LinkedTransferQueue

是 一 个 由 链 表 结 构 组 成 的 无 界 阻 塞 TransferQueue 队 列 。 相 对 于 其 他 阻 塞 队 列 ,
LinkedTransferQueue 多了 tryTransfer 和 transfer 方法。

  1. transfer 方法:如果当前有消费者正在等待接收元素(消费者使用 take()方法或带时间限制的
    poll()方法时),transfer 方法可以把生产者传入的元素立刻 transfer(传输)给消费者。如
    果没有消费者在等待接收元素,transfer 方法会将元素存放在队列的 tail 节点,并等到该元素
    被消费者消费了才返回。
  2. tryTransfer 方法。则是用来试探下生产者传入的元素是否能直接传给消费者。如果没有消费
    者等待接收元素,则返回 false。和 transfer 方法的区别是 tryTransfer 方法无论消费者是否
    接收,方法立即返回。而 transfer 方法是必须等到消费者消费了才返回。
    对于带有时间限制的 tryTransfer(E e, long timeout, TimeUnit unit)方法,则是试图把生产者传
    入的元素直接传给消费者,但是如果没有消费者消费该元素则等待指定的时间再返回,如果超时

9. LinkedBlockingDeque

是一个由链表结构组成的双向阻塞队列。所谓双向队列指的你可以从队列的两端插入和移出元素。
双端队列因为多了一个操作队列的入口,在多线程同时入队时,也就减少了一半的竞争。相比其
他 的 阻 塞 队 列 , LinkedBlockingDeque 多 了 addFirst , addLast , offerFirst , offerLast ,
peekFirst,peekLast 等方法,以 First 单词结尾的方法,表示插入,获取(peek)或移除双端队
列的第一个元素。以 Last 单词结尾的方法,表示插入,获取或移除双端队列的最后一个元素。另
外插入方法 add 等同于 addLast,移除方法 remove 等效于 removeFirst。但是 take 方法却等同
于 takeFirst,不知道是不是 Jdk 的 bug,使用时还是用带有 First 和 Last 后缀的方法更清楚。
在初始化 LinkedBlockingDeque 时可以设置容量防止其过渡膨胀。另外双向阻塞队列可以运用在
“工作窃取”模式中。

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

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

相关文章

Linux的软连接和硬链接

1.创建链接 首先ln --help 可以看到默认创建的链接是硬链接。若是要创建符号链接则需要使用-s 参数 格式是: ln 源文件 链接文件 或者 ln -s 源文件 链接文件 2.区别 首先我创建了a和b文件。 然后又分别建立了a的硬链接a2,b的符号链接b2 由图中即可看…

角色属性04----HP

添加两个变量,使用任意伤害事件来扣除HP,蓝图的方式和加速跑差不多 找到一个死亡动画,先ue4重定向ue5小银人,在ue5重定向ue4给低模人物 进入动画,创建hit把死亡动画给它,同时创建一个变量is_hit作为状态转换…

全国最大规模量子计算云平台重磅发布

8月19日,在2023中国算力大会主论坛上,中国移动携手中国电科发布“量子计算云平台”。这是目前国内最大规模的量子计算云平台,也是业界第一次实现“量子与通用算力统一纳管混合调度”的系统级平台。该发布标志着我国量子计算正在逐步走向实用化…

不要再错过晓程科技【300139】了-神奇指标网

8.24不要再错过晓程科技【300139】了 虽然 晓程科技的庄家操盘不怎么的,经常诱多发套吸筹。但是通过神奇指标系统来操盘基本可以完美吃到这几波冲高。包括今天一开盘就入场了,明天有调整的话看情况还可以低吸一口也是稳的。 我们看到今天5月到至今在这个…

服务器数据恢复-AIX PV完整镜像方法以及误删LV的数据恢复方案

AIX中的PV相当于物理磁盘(针对于存储来说,PV相当于存储映射过来的卷;针对操作系统来说,PV相当于物理硬盘),若干个PV组成一个VG,AIX可以将容量不同的存储空间组合起来统一分配。AIX把同一个VG的所…

【安装】MongoDB7安装MongoSH命令

MongoDB Shell Download | MongoDB 下载之后 解压 配置环境变量即可 以前使用 mongo命令 改为 mongosh 官方说明 安装mongosh MongoDB 中文手册 | MongoD Manual | 中文操作手册 | MongoDB 最新版 (whaleal.com) 安装 mongosh — MongoDB Shell

suricata安装以及流量抓包

suricata安装 先安装wazuh的agent上篇博客有提到。Wazuh安装及使用_无所不知的神奇海螺的博客-CSDN博客 与wazuh联动,所以查看wazuh官方文档Network IDS integration - Proof of Concept guide Wazuh documentation 配置要求 跟着配置一步步走就行 到这一步&am…

主力资金指标公式-神奇指标网

主力资金: VA1:100-3*SMA((CLOSE-LLV(LOW,65))/(HHV(HIGH,80)-LLV(LOW,65))*100,20,1)2*SMA(SMA((CLOSE-LLV(LOW,65))/(HHV(HIGH,80)-LLV(LOW,65))*100,20,1),15,1); VARA:EMA(VAR9,3); VARB:(VAR9-VARA)/2; 大盘资金:VARB,COLORGREEN,LINETHICK2; …

聚水潭无需API开发连接伙伴云,实现新增售后申请单自动汇总到表单

聚水潭用户使用场景: 电商行业通常使用聚水潭作为企业的ERP系统。每当聚水潭有新的售后申请时,企业人员常常需要将订单信息手动复制并录入到伙伴云存储、汇总,包括订单单号、状态、金额等20多项信息。这种人工手动复制和录入的方式容易导致订…

vue直接使用高德api

第一步&#xff1a;在index.html 引入 <script src"https://webapi.amap.com/maps?v2.0&key你的key"></script>第二步&#xff1a;在你需要地图的时候 放入 <template><div style"width: 200px; height: 200px"><div id&q…

浅谈电力电容器的在线监测技术与选型

安科瑞 华楠 【摘要】传统的电力电容器检测通常为断电,离线进行,影响了生产。已有的电力电容器在线诊断技术集中于对电容量、介质损耗角的测量,检测结果滞后于故障的发生,且检测结果并不理想。主要针对电力系统中高压电力电容器的常见故障,对其故障中发生放电现象的机理进行了…

【腾讯云 Cloud studio 实战训练营】基于Claude快速完成Excel工资自动核算

目录 1 什么是Cloud Studio&#xff1f;2 注册与代码管理2.1 账号注册2.2 Git关联 3 实战&#xff1a;Excel工资自动核算3.1 创建项目与配置3.2 “念咒师”Claude GPT3.3 代码编写与运行 4 个人开发感受 1 什么是Cloud Studio&#xff1f; Cloud Studio是腾讯云为开发者提供的…

超越界限:大模型应用领域扩展,探索文本分类、文本匹配、信息抽取和性格测试等多领域应用

超越界限&#xff1a;大模型应用领域扩展&#xff0c;探索文本分类、文本匹配、信息抽取和性格测试等多领域应用 随着 ChatGPT 和 GPT-4 等强大生成模型出现&#xff0c;自然语言处理任务方式正在逐步发生改变。鉴于大模型强大的任务处理能力&#xff0c;未来我们或将不再为每…

C#获取DataTable的前N行数据然后按指定字段排序

获取DataTable的前N行数据然后按指定字段排序 可以使用以下三种代码&#xff1a; 第一种&#xff1a;使用Linq DataTable dtLast dataTable.AsEnumerable().Take(count).OrderBy(dataRow > Convert.ToInt32(dataRow["Sequence"])).CopyToDataTable(); 第二种…

Mysql-InnoDB记录结构

一、InnoDB简介 InnoDB 采取的方式是&#xff1a;将数据划分为若干个页&#xff0c;以页作为磁盘和内存之间交互的基本单位&#xff0c;InnoDB中页的大小一般为 16 KB。也就是在一般情况下&#xff0c;一次最少从磁盘中读取16KB的内容到内存中&#xff0c;一次最少把内存中的1…

Hadoop入门机安装hadoop

0目录 1.Hadoop入门 2.linux安装hadoop 1.Hadoop入门 定义 Hadoop是一个由Apache基金会所开发的分布式系统基础架构。用户可以在不了解分布式底层细节的情况下&#xff0c;开发分布式程序。充分利用集群的威力进行高速运算和存储。 优势 高可靠性&#xff1a;Hadoop底层维护多…

智慧互联,有序充电--多场景充电

企业微电网能效及充电管理解决方案 安科瑞 崔丽洁 1、企业需求&#xff08;目的地充电&#xff09; 站在企业的角度&#xff0c;除了要主动承担碳达峰、碳中和的社会责任&#xff0c;也需要考虑自身的经营和利润&#xff0c;需要结合企业的现状进行改造 企业微电网平台——与…

OLED透明屏直销:高性价比与便捷购买的首选

OLED透明屏作为一项创新的显示技术&#xff0c;其透明度和高清晰度的特点使其在各个领域得到了广泛应用。 在购买OLED透明屏时&#xff0c;传统的渠道如经销商和代理商可能增加额外的成本和环节。 然而&#xff0c;OLED透明屏的直销模式为消费者提供了更便捷和高性价比的购买…

iOS App逆向之:iOS应用砸壳技术

在iOS逆向&#xff0c;有一项关键的技术叫做“iOS砸壳”&#xff08;iOS App Decryption&#xff09;。自iOS 5版本以来&#xff0c;苹果引入了应用程序加密机制&#xff0c;使得大部分应用都需要进行砸壳操作才能进行逆向分析。因此作为开发者、逆向工程师和安全研究人员都需要…

PostgreSQL下载路径与安装步骤

PgSQL介绍 PgSQL和MySQL一样是一种关系模型的数据库&#xff0c;全称为PostgreSQL 数据库。 优势&#xff1a;PgSQL是一种可扩展、可靠、可定制的数据库管理系统&#xff0c;具有良好的数据完整性和安全性&#xff0c;支持多种操作系统&#xff0c;包括 Linux、Windows、MacOS …