如何理解队列
(1)操作受限的线性数据结构
(2)特点:先进先出、后进后出
(3)操作:入队(将新的元素添加到末尾)、出队(将元素从队首移出)
(4)应用:循环队列、阻塞队列、并发队列。应用于偏底层的框架和中间件,如Disruptor高性能队列、Linux环形队列都用到了循环并发队列
几种队列形式
顺序队列:
用数组实现的队列
实现思路:
(1)需要两个指针,一个指向队头的指针,一个指向队尾的指针。
(2)当有新的元素入队的时候,队尾的指针就往后移动
(3)当有元素出队的时候,队首的指针也往后移动
问题
(1)队列出队会导致数组数据不连续,当入队时,没有空闲空间的时候,需要集中触发一次数据搬移操作。
链式队列:
基于链表实现的队列。
实现思路:
和顺序队列实现方式相似,只是一个是基于数据实现,一个是基于链表实现。
循环队列:
前提:顺序队列的出队操作会导致数据不连续,从而会有数据搬移的操作,入队的性能会有影响。循环队列可以解决出队造成的数据不连续的情况。
如图所示,可以对循环队列有一个清楚的认识。将数组的首尾部相连形成了一个环,生成一个基于数据实现的循环队列。
实现关键:确定好队空和队满的判断条件
1、队空(head==tail)
2、队满 (tail+1)%n = head
![](https://img.haomeiwen.com/i13389758/fa2c75d4f4a14f7d.png)
阻塞队列
队列基础上增加了阻塞的功能,就是一个生产者-消费者模型
(1)队列为空的时候,从队头取数据会被阻塞
(2)队列慢的时候,队尾插数据会被阻塞
优点:有效协调生产和消费的速度,还可以协调生产者和消费者的个数来提高处理效率
![](https://img.haomeiwen.com/i13389758/374ba2b55b2c9a05.png)
并发队列(线程安全的队列)
实现方式:enqueue()、dequeue()方法上加锁,锁粒度大并发°比较低,同一时刻只允许一个存或取操作。
写在最后
问题:线程池没有空闲线程的时候,新的任务请求线程资源,将请求排队,等有空闲线程时,取出排队请求继续处理,如何存储排队的请求
公平的处理排队请求,满足先进者先出等特点,适合用队列来存储
(1)链式队列,支持一个无限排队的无界队列,会导致过多的请求排队,响应时间过长,对于响应时间敏感的系统不合适。
(2)顺序队列,支持数据实现的有界队列,队列大小有限,请求超过队列大小的请求会被拒绝。适合响应时间敏感的系统(设置合理的队列大小,太大会导致请求太多,太小无法充分利用系统资源)
大部分资源有限的场景,当没有空闲资源时,基本都可以通过队列的数据结构来实现请求排队。
还有哪些场景会用到排队请求:
分布式消息队列
关于队列实现的几个demo已经上传到github
网友评论