关于链式队列
链式队列又称为链队,是使用单链表实现的,需要一个头指针一个尾指针
结构图:
链队需要的元素组成
/*链式队列的每一个节点*/
struct node{
int data;//存储数据
struct node *next;//指向下一个节点的指针
};
/*链式队列*/
typedef struct{
struct node *head;//头指针
struct node *tail;//尾指针
}LinkedQueue;
创建一个带头节点的空队列
- 创建一个节点p
- 将p节点的next指向null
- 创建一个队列
- 将队列的head指针指向节点p
- 将队列的tail指针指向节点p
创建出空节点的结构图(实际创建出来没有p这个指针)
/*初始化一个空的链式队列*/
LinkedQueue *initLinkedQueue()
{
LinkedQueue *linkedQueue = (LinkedQueue *)malloc(sizeof(LinkedQueue));//创建队列
struct node *p = (struct node *)malloc(sizeof(struct node));//创建第一个空节点
p->next = NULL;//让第一个节点的next指向null
linkedQueue->head = linkedQueue->tail = p;//将队列的head和tail指针指向第一个节点
return linkedQueue;
}
入队操作
对于链式队列不必考虑队列满不满,因为永远不会满
1. 创建一个新的节点q
2. 将传入的数据赋值给q的data
3. q的next指针指向null
4. 将队列的tail指针指向的节点的next指针指向q节点
5. 队列的tail指针指向新插入的那个q节点,tail永远指向最后一个节点
/*入队操作*/
void insert(LinkedQueue *lq, int num)
{
struct node *q = (struct node *)malloc(sizeof(struct node));//在内存中申请一个新的节点
q->data = num;//给新节点传入数据
q->next = NULL;//新节点的next指针为空
lq->tail->next = q;//将尾节点所指的那个节点的下一个节点指向新节点
lq->tail = q;//尾指针指向新插入的节点
}
出队操作
- 声明一个节点q
- 如果队列不为空,让q指向头节点后面的那个节点,也就是要删除的那个节点
- 让队列的头节点的next指向q所指节点 的后面的那个节点
- 将q所指节点的data保存起来
- 销毁q所指的那个节点(free(q))
- 注意如果只有最后一个节点出队了,tail指针所指的节点内存已被回收,所以需要对tail指针做处理,让队列的head指针=tail指针
/*删除队列元素*/
int delete(LinkedQueue *lq, int *temp)
{
struct node *q;
if (isEmpty(lq)) {
printf("队列为空!\n");
return 0;
}
else {
q = lq->head->next;//让q指向头节点后面的那个节点
lq->head->next = q->next;//让队列的头节点的next指向q所指节点 的后面的那个节点
*temp = q->data;//将q所指节点的data保存起来
free(q);// 销毁q所指的那个节点,回收内存
//当只有一个元素的时候,出队后队列为空,此时要修改尾指针
if (lq->head->next == NULL) {
lq->head = lq->tail;
}
return 1;
}
}
使用C语言实现链式队列
#include<stdio.h>
#include<stdlib.h>
/*链式队列的每一个节点*/
struct node{
int data;
struct node *next;
};
/*链式队列*/
typedef struct{
struct node *head;
struct node *tail;
}LinkedQueue;
/*初始化一个空的链式队列*/
LinkedQueue *initLinkedQueue()
{
LinkedQueue *linkedQueue = (LinkedQueue *)malloc(sizeof(LinkedQueue));
struct node *p = (struct node *)malloc(sizeof(struct node));
p->next = NULL;
linkedQueue->head = linkedQueue->tail = p;
return linkedQueue;
}
/*入队操作*/
void insert(LinkedQueue *lq, int num)
{
struct node *q = (struct node *)malloc(sizeof(struct node));//在内存中申请一个新的节点
q->data = num;//给新节点传入数据
q->next = NULL;//新节点的next指针为空
lq->tail->next = q;//将尾节点所指的那个节点的下一个节点指向新节点
lq->tail = q;//尾指针指向新插入的节点
}
/*判断队列是否为空*/
int isEmpty(LinkedQueue *lq)
{
if (lq->head == lq->tail){//如果头尾指针指向一个,队列就是为空的
return 1;
}
else {
return 0;
}
}
/*删除队列元素*/
int delete(LinkedQueue *lq, int *temp)
{
struct node *q;
if (isEmpty(lq)) {
printf("队列为空!\n");
return 0;
}
else {
q = lq->head->next;
lq->head->next = q->next;
*temp = q->data;
free(q);
//当只有一个元素的时候,出队后队列为空,此时要修改尾指针
if (lq->head->next == NULL) {
lq->head = lq->tail;
}
return 1;
}
}
/*遍历队列*/
void display(LinkedQueue *lq)
{
struct node *q = lq->head->next;
while (q != NULL) {
printf("队列元素为%d\n", q->data);
q = q->next;
}
}
int main()
{
LinkedQueue *lq = initLinkedQueue();
insert(lq, 1);
insert(lq, 2);
insert(lq, 3);
insert(lq, 4);
insert(lq, 5);
int temp = 0;
delete(lq, &temp);
printf("%d\n", temp);
display(lq);
return 0;
}