一、链队列简介。
和链栈相似,适用于动态存储,由于是先进先出原则,因此可以用单链表表示队列,并设置一个头指针(front)和一个尾指针(rear),入队时,尾指针(rear)后移,出队时,头指针(front)后移。
二、具体操作
1.结构体定义和初始化
采用结构体套用的方法,链表的结构中有前指针和后指针,而结点中有数据域和直接后继域。
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#define true 1
#define false 0
typedef struct node{ //数据结点的结构
int data;
struct node *next;
}*Lnode;
typedef struct Lteam{ //链表的结构
Lnode front;
Lnode rear;
}*lteam;
2.初始化
同理,初始化时候需要申请一个链表的结构,还需要申请一个结点的结构,并把结点结构置空。
//初始化队列
void InitLteam(lteam &L){
Lnode p=(node *)malloc(sizeof(node));
L=(Lteam *)malloc(sizeof(Lteam));
p->next=NULL;
L->front=L->rear=p;
}
3.判队空
链队中队空的条件只有 队头指针等于队尾指针时。
//判队空
int empty(lteam L){
if(L->front==L->rear){
return true;
}else return false;
}
4.入队
入队时只需要申请数据结点,然后针对尾指针和数据结点进行单链表的尾插法。
//入队
int pushLteam(lteam &L,int x){
Lnode p=(node *)malloc(sizeof(node));
p->data=x;
p->next=NULL;
L->rear->next=p; //一定要对尾指针进行操作
L->rear=p;
}
5.出队
出队时需要判断队满,后对头指针和数据结点进行单链表的删除操作。
//出队
int popLteam(lteam &L,int &x){
Lnode p;
if(empty(L)==1){
printf("队空!");
return false;
}else{
p=L->front->next;
L->front->next=p->next; //一定要对头指针进行操作
x=p->data;
free(p);
printf("\n%d出队",x);
if(L->front->next==NULL){ //判断队中是不是只有一个元素,如果是则进行队空处理。
L->front=L->rear;
return true;
}
}
}
6.遍历
定义一个结点指针,指向第一个数据结点,如果存在输出并往后移动。
//遍历队列
int bianli(Lteam *L){
if(empty(L)==1){
printf("队空!");
return false;
}else{
Lnode p;
p=L->front->next;
while(p!=NULL){
printf("%d ",p->data);
p=p->next;
}
}
}
7.取队头
//求队头
int gettop(lteam L){
int p;
if(empty(L)==1){
printf("队空!");
return false;
}else{
p=L->front->next->data;
printf("%d",p);
return p;
}
}
8.具体操作
int main(){
lteam s;
int w;
InitLteam(s);
printf("-----------1-5入队--------------");
pushLteam(s,1);
pushLteam(s,2);
pushLteam(s,3);
pushLteam(s,4);
pushLteam(s,5);
printf("\n此时队列为:");
bianli(s);
printf("\n-----------1-2出队--------------");
popLteam(s,w);
popLteam(s,w);
printf("\n此时队列为:");
bianli(s);
printf("\n队头为:");
gettop(s);
}
9.运行结果: