队列是一种先进先出的数据结构:即插入在表的一端(队尾)进行,删除在表的另一端(队头)进行
与线性表相似,队列也有顺序储存和链式储存两种储存方法;实现方法和代码如下(运用了模板类;详细说明在注释中)
下面是一个循环顺序储存队列的实现
这里要特别注意注意队头元素在队列中下标是front的下一个数
#define MAX_SIZE 61
template<typename T>
struct queue{
T data[MAX_SIZE];
int front,back;
//front队头指针:指向队头元素;
//back队尾指针 :指向队尾元素
int num;//记录队列中元素个数 ,用以判断队满对空
};
template<typename T>
queue<T> *create()
{
queue<T> *p;
p = new queue<T>;
p->back = p->front =MAX_SIZE-1;
p->num = 0;
return p;
}
//push()入队列:在队列尾添加一个数据
template<typename T>
void push(queue<T> *q,T data)
{
if(q->num == MAX_SIZE)
{
cout<<" 队满"<<endl;
return ;
}
else{
q->back=(q->back+1) % MAX_SIZE;//解决假溢出
q->data[q->back] =data;
q->num++;
return;
}
}
//pop()删除队列头的一个数据,并返回该值
template<typename T>
T pop(queue<T> *q)
{
if(q->num == 0)
{
cout << " 队列空";
return 0;
}else
{ T x = q->data[(q->front+1)%MAX_SIZE];
q->front=(q->front+1)%MAX_SIZE;
q->num--;
return x;
}
}
//empty()是检查是否为空的方法
template<typename T>
bool empty(queue<T> *q)
{
if(q->num == 0)
return 1;
else
return 0;
}
//输出队列的基本信息
template<typename T>
void output(queue<T> *q)
{
if(empty(q)){
cout<<" 队列空!";
return;
}
int t = q->front,i=2;
t=(t+1)%MAX_SIZE;
cout<<" 队头元素为"<<q->data[t]<<endl;//注意队头元素下标是front的下一个
while(t != q->back && (t+1)%MAX_SIZE != q->back )
{ t=(t+1)%MAX_SIZE;
cout<<" 第"<<i<<" 号元素为"<<q->data[t]<<endl;
i++;
}
cout<<" 队尾元素为"<<q->data[q->back]<<endl;
cout<<" 该队列元素个数为:"<<q->num<<endl<<endl;
}
int main()
{
queue<int> *q;
q = create<int>();
output(q);
cout<<endl;
for(int i=1;i<5;i++)
{
push(q,i);
cout<<" 将"<<i<<" 入队"<<endl;
}
cout<<endl;
output(q);
cout<<" 将队头元素"<<pop(q)<<" 出队"<<endl;
output(q);
}
template<typename T>
struct Node{//链队的节点类型
T data;
Node *next;
};
//头指针font和尾指针back是两个独立的指针变量,共同标示这个链队;
//因此从结构上考虑,将二者封装在一个结构中
template<typename T>
struct Queue{ //将头尾指针封装在一起的链队
Node<T> *font;
Node<T> *back;
};
//队列初始化
template<typename T>
Queue<T>* create(Queue<T>* q)//用指向头尾指针节点的变量q表示 这个队列
{
//Queue *q;
Node<T> *p;
q = new Queue<T>; //申请头尾指针节点
p = new Node<T>;//申请链队头结点
p->next = NULL;
q->back = q->font = p;
return q;
}
//入队push():在队列尾添加一个数据
template<typename T>
void push(Queue<T> *q,T data)
{
Node<T> *p ;
p = new Node<T>;
p->data = data;
p->next = NULL;
q->back->next = p;//将队列的尾节点指向新节点
q->back = p;//将尾指针指向新入队的新节点
return;
}
//出队列:pop()删除队列头的一个数据,并返回该值
template<typename T>
T pop(Queue<T> *q)
{
if(empty(q)){
cout<<" 队满"<endl;
return; }
else
{
Node<T> *p = q->font->next;//p指向要出队的节点
q->font->next = p->next;//头指针指向新的队头
T x = p->data;
delete p;
if(q->back->next == NULL)
q->back =q->font;//只有一个元素时,出队后队空,此时还要修改队尾指针
return x;
}
}
//empty()是检查是否为空的方法
bool empty(Queue<T> *q)
{
if(q->back == q->font)
return 1;
else return 0;
}
//size()队列中元素个数
template<typename T>
int size(Queue<T> *q)
{
Node<T> *p = q->font->next;
int count = 0;
while(p != NULL )
{
count++;
p=p->next;
}
return count;
}
//front()获得队列最前面一个元素
template<typename T>
T front(Queue<T> *q)
{ if(!empty(q))
return q->font->next->data;
else
cout<<" 栈为空!"<<endl;
}
//back()返回队列最后一个元素的值
template<typename T>
T back(Queue<T> *q)
{
if(!empty(q))
return q->back->data;
else
cout<<" 栈为空!"<<endl;
}
//输出队列的基本信息
template<typename T>
void output(Queue<T> *q)
{
if(empty(q))
{
cout<<" 该队列为空队列!"<<endl;
return;
}
Node<T> *p;
p=q->font->next;
cout<<" 队头元素为:"<<front(q)<<endl;
int i = 1;
while(p->next->next != NULL)
{
cout<<" 第"<<++i<<" 号元素为"<<p->next->data<<endl;
p=p->next;
}
cout<<" 队尾元素为:"<<back(q)<<endl;
cout<<" 该队列中共有"<<size(q)<<" 个元素"<<endl<<endl;
}
int main()
{
Queue<int> *q ;
//这里由于没有传入能让编译器识别出T的信息,所以要指出T为int
q = create<int>();
output(q);
cout<<endl;
for(int i=1;i<5;i++)
{
push(q,i);
cout<<" 将"<<i<<" 入队"<<endl;
}
cout<<endl;
output(q);
cout<<" 将队头元素"<<pop(q)<<" 出队"<<endl;
output(q);
}
https://download.csdn.net/download/qq_45768060/12297131