统一C语言风格定义各种数据结构及基本操作——链队列基本操作

/*linkqueue.h*/
#pragma once
#include<stdio.h>
#include<stdlib.h>

typedef int ElemType;
typedef struct LNode { //线性表的链式存储结构定义
	ElemType data;
	struct LNode* next;
}LNode, *LinkList;
typedef struct LinkQueue {//队列存储结构
	LinkList front;//队头指针
	LinkList rear;//队尾指针
}LinkQueue,*pLinkQueue;
//初始化队列
int initQueue(pLinkQueue plq)
{
	plq->front = (LNode*)malloc(sizeof(LNode));
	if (!plq->front) return 0;
	plq->rear = plq->front;//初始时尾指针和头指针指向同一结点(这样尾指针在第一次更新时,更新所指结点的next指针实际上也就是头指针所指结点的next指针)
	plq->front->next = plq->rear->next = NULL;//将数据域与指针域均置空
}
//向队尾插入元素(这里需要注意的是头指针所指向结点不存放数据,只有一个指向下一个结点的next指针;而尾指针则不断更新指向最后一个结点)
int pushQueue(pLinkQueue plq, ElemType e)
{
	LNode* L = (LNode*)malloc(sizeof(LNode));//新开辟一个结点
	if (!L)return 0;
	L->data = e;
	L->next = NULL;
	plq->rear->next = L;//尾指针指向新开辟结点
	plq->rear = L;//更新尾指针
	return 1;
}
//从头部删除元素
int popQueue(pLinkQueue plq, ElemType& e)
{
	if (plq->front == plq->rear)return 0;//队列为空
	LNode* L = plq->front->next;//新声明一个指针变量指向头指针所指向结点的下一个结点
	e = L->data;
	plq->front->next = L->next;//队头结点指针域指向所删除结点的下一个结点
	//if (plq->front == plq->rear)//若删除的是尾结点,通过比较发现,删除后头尾结点并不相等
	//	printf("相等!\n");
	if (L == plq->rear)//若删除的是尾结点,plq->front->next = L->next会使得头结点指针域为空,而尾节点指针域本身也为空,头节点和尾节点成了两个完全独立且不再有联系的空间
		plq->rear = plq->front;//因此这里需要将尾指针指向头指针所指向的区域,此时数据域和指针域再次全部置空,头、尾指针再次指向同一区域
	free(L);//释放指针
	return 1;
}
//判断是否为空
int isEmptyQueue(pLinkQueue plq)
{
	if (plq->front->next == NULL)return 1;
	return 0;
}
//获取队头元素
int getHeadQueue(pLinkQueue plq,ElemType& e)
{
	if (plq->front == plq->rear)return 0;
	e = plq->front->next->data;
	return 1;
}
//清空队列
void clearQueue(pLinkQueue plq)
{
	plq->front->next = plq->rear->next = NULL;//将数据域与指针域均置空
}
//销毁队列
int destroyQueue(pLinkQueue plq)
{
	while (plq->front) {
		plq->rear = plq->front->next;
		free(plq->front);
		plq->front = plq->rear;
	}
	return 1;
}
void traverseQueue(pLinkQueue plq, void(*callback)(ElemType)) {
	LNode* L = plq->front->next;
	while (L) {
		(*callback)(L->data);
		L = L->next;
	}
	printf("\n");
}
void lqprint(ElemType e)
{
	printf("%d ", e);
}
/*main.cpp*/
#include"linkqueue.h"

int main()
{
	LinkQueue lq;
	int i = 0, e, state;

	state = initQueue(&lq);
	if (state)
		printf("链队列初始化成功!\n");
	else
		printf("链队列初始化失败!\n");

	printf("向链队列中尾插元素!\n");
	while (1)
	{
		printf("尾插第%d个元素:", ++i);
		scanf("%d", &e);
		if (e == -999)break;
		state = pushQueue(&lq, e);
		if (!state) {
			printf("插入失败!\n");
			break;
		}
	}
	printf("遍历队列中元素为:");
	traverseQueue(&lq, lqprint);

	printf("\n头删队列中一个元素!\n");
	state = popQueue(&lq, e);
	printf("删除成功!删除的元素为%d\n", e);
	printf("遍历队列中元素为:");
	traverseQueue(&lq, lqprint);

	getHeadQueue(&lq, e);
	printf("\n队列头元素:%d\n\n", e);

	printf("清空队列!\n");
	clearQueue(&lq);
	printf("队列是否为空[1-空,0-不空]:%d\n",isEmptyQueue(&lq));

	printf("销毁队列!\n");
	destroyQueue(&lq);
	return 1;
}

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值