队列的顺序存储
2016-11-09 16:30
232 查看
队列:
插入数据:队尾(队尾的位置为空)
删除数据:队头
顺序队列:
建立一个长度为大于n的数组,把队列的所有元素存储在数组的前n个单元上,数组下标为0的一端为队头
入队操作即在队尾插入一个元素,时间复杂度为0(n)
出队操作在对头,由于固定下标为0的位置为队头,当出队列时,需要队列中的所有元素都要向前移动。
为了避免当只有一个元素时,队头和对尾的处理变得麻烦,所以引入两个指针。
front指向队头,rear指向队尾,若front=rear时,不是满队就是空队
但是还是存在问题:
假溢出:
解决假溢出的问题,当后面的位置满了,从头开始。队列的这种头尾相接的顺序存储结构成为循环队列。
新问题:无法确定队列是空还是满
办法1:设置一个flag,当flag==0 && rear==front,为空
当flag==1 && rear==front 为满
办法2:在队列满时,数组中还剩一个位置。
由于是循环的操作,rear可能大于front也可能小于front
如图
判断队列的状态为:
队满的条件:
左图为rear大于front,队满的条件是(rear+1)%QueueSize== front
右图为rear小于front,队满的条件是(rear+1)==front
综上:队满的条件是:(rear+1)%QueueSize== front
队空的条件:
rear == front
队列长度的计算:
当rear大于front时,长度等于 rear-front
当rear小于front时,(证明又循环了)长度等于MAXSIZE-front的下标
加上 rear的下标+0,就等于MAXSIZE+rear-front
综上:队长的公式为:(rear-front+QueueSize)%QueueSize
代码实现:
插入数据:队尾(队尾的位置为空)
删除数据:队头
顺序队列:
建立一个长度为大于n的数组,把队列的所有元素存储在数组的前n个单元上,数组下标为0的一端为队头
入队操作即在队尾插入一个元素,时间复杂度为0(n)
出队操作在对头,由于固定下标为0的位置为队头,当出队列时,需要队列中的所有元素都要向前移动。
改进1
不去限制队列中的元素必须存储在数组的前n个单元,即<font color=red>队头不一定是下标为0的位置</font>
为了避免当只有一个元素时,队头和对尾的处理变得麻烦,所以引入两个指针。
front指向队头,rear指向队尾,若front=rear时,不是满队就是空队
但是还是存在问题:
假溢出:
改进2:
循环队列:解决假溢出的问题,当后面的位置满了,从头开始。队列的这种头尾相接的顺序存储结构成为循环队列。
新问题:无法确定队列是空还是满
办法1:设置一个flag,当flag==0 && rear==front,为空
当flag==1 && rear==front 为满
办法2:在队列满时,数组中还剩一个位置。
由于是循环的操作,rear可能大于front也可能小于front
如图
判断队列的状态为:
队满的条件:
左图为rear大于front,队满的条件是(rear+1)%QueueSize== front
右图为rear小于front,队满的条件是(rear+1)==front
综上:队满的条件是:(rear+1)%QueueSize== front
队空的条件:
rear == front
队列长度的计算:
当rear大于front时,长度等于 rear-front
当rear小于front时,(证明又循环了)长度等于MAXSIZE-front的下标
加上 rear的下标+0,就等于MAXSIZE+rear-front
综上:队长的公式为:(rear-front+QueueSize)%QueueSize
代码实现:
#include <iostream> using namespace std; #include<stdio.h> #include<stdlib.h> #include<time.h> #define OK 1 #define ERROR 0 #define TRUE 1 #define FALSE 0 #define MAXSIZE 20 /* 存储空间初始分配量 */ typedef int Status; typedef int QElemType; typedef struct{ QElemType data[MAXSIZE]; int front ; //头指针 int rear ; //尾指针 指向空的位置 }SqQueue; Status InitQueue(SqQueue *Q){ Q->front = 0; Q->rear = 0; return OK; } Status EnQueue(SqQueue *Q,QElemType e){ if((Q->rear+1)%MAXSIZE == Q->front) //包含两种情况,rear<front 差一个位置队满 //rear>front 差一圈(一个MAXSIZE)队满 return ERROR; Q->data[Q->rear] = e; Q->rear = (Q->rear+1)%MAXSIZE; //当数组中后面的位置栈满,从头开始 return OK; } Status DeQueue(SqQueue *Q,QElemType *e){ if(Q->front == Q->rear) //队空的判断 return ERROR; *e = Q->data[Q->front]; Q->front = (Q->front+1)%MAXSIZE; //移动到数组最后位置,从头开始 return OK; } int QueueLength(SqQueue Q){ return (Q.rear+MAXSIZE-Q.front)%MAXSIZE; } Status GetHead(SqQueue q,QElemType *e){ if(q.front == q.rear) //队列为空 return ERROR; *e = q.data[q.front]; return OK; } int main() { SqQueue q ; InitQueue(&q); for(int i=0;i<10;i++){ EnQueue(&q,i); } printf("元素进队列的顺序为\n"); for(int i=0;i<10;i++){ printf("%d\n",q.data[i]); } printf("队列的元素个数为%d\n",QueueLength(q)); int value ; GetHead(q,&value); printf("队列的head的值为%d\n",value); printf("元素出队列的顺序为\n"); int result; for(int i=0;;i++){ if(q.front == q.rear) break; DeQueue(&q,&result); printf("%d\n",result); } return 0; }
相关文章推荐
- 队列(顺序存储) java实现
- 队列的顺序存储和链式表示方法-数据结构学习笔记2.3
- 队列——顺序存储与链式存储
- 顺序表(顺序存储)循环队列类(初始化,入队,退队,输出排头与排尾指针及元素)
- 学习笔记------数据结构(C语言版) 队列的顺序存储/循环队列
- 队列的顺序存储
- 队列的顺序存储和实现
- 队列之顺序存储实现
- 队列的顺序存储表示---数组实现
- C++实现循环队列之顺序存储
- 循环队列--队列的顺序存储表示形式[原创]
- 队列的顺序存储
- 循环队列-顺序存储-Java实现
- 队列的顺序存储
- 线性表(List)---队列的顺序存储
- 队列的顺序存储——循环队列
- 队列——顺序存储的循环队列(存储元素为自定义类型)
- 队列的顺序存储
- 队列的顺序存储与链式存储
- Java使用顺序存储实现队列