一、什么是队列
队列:具有一定操作约束的线性表
插入和删除操作:只能在一端插入,而在另一端删除,发生在队列的两头
- 数据插入:入队列
- 数据删除:出队列
- 先来先服务
- 先进先出:FIFO
二、队列的抽象数据类型描述
类型名称:队列
数据对象集:一个有0个或多个元素的有穷线性表
操作集:长度为MaxSize的队列Q∈Queue,队列元素item∈ElementType
三、队列的顺序存储实现
队列的顺序存储结构通常由一个一维数组和一个记录队列头元素位置的变量front以及一个记录队列尾元素位置的变量rear组成
举个例子:
-
一开始front和rear都是-1,队列为空
-
加入一个工作,rear指向下标为0的地方
-
下面删除一个任务,front指向这个队列里第一个元素的再前面一个
-
那么,加满以后,再想加入元素已经加入不进去了,但队列的前面还是空的,怎么办呢?
四、循环队列
- 加入元素
- 加到这个时候,如果rear再加1,就和front相等了。代表队列是空的还是满的呢?
问题:为什么会出现这种空队列、满队列无法区分呢?
front与rear的差距有n种情况:0,1,2,3,4,5…,n
队列装载元素个数情况有n+1种:0(空队列),1(一个元素),2,3,4,5,6…,n+1
解决方案: - 使用额外标记:Size或者tag域。size用来记录当前队列的元素个数,看size是否等于0。用一个标记tag,当插入一个元素的时候,tag设为1,删除一个元素的时候tag设为0
- 仅使用n-1个数组空间
五、队列顺序存储方式相应操作
- 入队列
- 出队列
六、队列链式存储方式及其相应操作
队列的链式存储结构也可以用一个单链表实现。插入和删除操作分别在链表的两头进行;队列指针front和rear应该分别指向链表的哪一头呢?
- front是要做删除操作,rear是要做插入操作
- 所以单链表的头是front,尾部是rear
** 不带头结点的链式队列出队操作的一个实例**