数据结构 - 链队列的实行(C语言)
一、什么是链队列?
队列的链式存储结构,其实就是线性表的单链表,只不过它只能尾进头出而已,我们把它简称为链队列。为了操作上的方便,我们将队头指针指向链队列的头结点,而队尾指针指向尾结点,如下图所示:
空队列时,front和rear都指向头结点,如下图所示。
链队列的结构为:
typedef int QElemType; /* QElemType类型根据实际情况而定,这里假设为int */
/* 结点结构 */
typedef struct QNode
{
ElemType data;
struct QNode *next;
}QNode;
/* 队列的链表结构 */
typedef struct
{
QNode *front; // 队头指针
QNode *rear; // 队尾指针
}LinkQueue;
二、基本操作
2.1 初始化操作
实现代码如下:
// 初始化链队列操作
Status initQueue(LinkQueue *Q)
{
Q->front = Q->rear = (Node *)malloc(sizeof(Node));
if (!Q->front)
return FALSE;
Q->front->next = NULL;
return TRUE;
}
2.1 入队操作
人队操作时,其实就是在链表尾部插入结点,如下图所示:
实现代码如下:
// 入队操作
Status enQueue(LinkQueue *Q, ElemType e)
{
Node *s = (Node *)malloc(sizeof(Node));
if (!s)
return FALSE;
s->data = e;
s->next = NULL;
Q->rear->next = s; // 把拥有元素e的新结点s赋值给原队尾结点的后继
Q->rear = s; // 把当前的s设置为队尾结点,rear指向s
return TRUE;
}
2.3 出队操作
出队操作时,就是头结点的后继结点出队,将头结点的后继改为它后面的结点,若链表除头结点外只剩一个元素时,则需将rear指向头结点,如下图所示:
实现代码如下:
// 出队操作
Status deQueue(LinkQueue *Q, ElemType *e)
{
Node *p;
if (Q->front == Q->rear)
return FALSE;
p = Q->front->next; // 将欲删除的队头结点暂存给p,见图中①
*e = p->data; // 将欲删除的队头结点的值赋值给e
Q->front->next = p->next; // 将原队头结点的后继p->next赋值给头结点后继,见图中②
if (Q->rear == p) // 若队头就是队尾,则删除后将rear指向头结点,见图中③
Q->rear = Q->front;
free(p);
return TRUE;
}
2.4 遍历操作
实现代码如下:
// 遍历队列操作
Status tarverseQueue(const LinkQueue Q)
{
Node *p;
p = Q.front->next;
while (p)
{
printf("%d ", p->data);
p = p->next;
}
printf("\n");
return TRUE;
}
三、完整程序
#include <stdio.h>
#include <stdlib.h>
#define TRUE 1
#define FALSE 0
#define MAXSIZE 20 /* 存储空间初始分配量 */
typedef int Status;
typedef int ElemType; /* ElemType类型根据实际情况而定,这里假设为int */
/* 结点结构 */
typedef struct Node
{
ElemType data;
struct Node *next;
}Node;
/* 队列的链表结构 */
typedef struct
{
Node *front; // 队头指针
Node *rear; // 队尾指针
}LinkQueue;
Status initQueue(LinkQueue *Q); // 初始化链队列操作
Status enQueue(LinkQueue *Q, ElemType e); // 入队操作
Status deQueue(LinkQueue *Q, ElemType *e); // 出队操作
Status tarverseQueue(const LinkQueue Q); // 遍历队列操作
Status destroyQueue(LinkQueue *Q); // 销毁队列操作
Status clearQueue(LinkQueue *Q); // 清空队列操作
Status isEmpty(const LinkQueue Q); // 判断是否为空队列
Status getHead(const LinkQueue Q, ElemType *e); // 获得队头元素
int getLength(const LinkQueue Q); // 获得队列的长度
// 初始化链队列操作
Status initQueue(LinkQueue *Q)
{
Q->front = Q->rear = (Node *)malloc(sizeof(Node));
if (!Q->front)
return FALSE;
Q->front->next = NULL;
return TRUE;
}
// 入队操作
Status enQueue(LinkQueue *Q, ElemType e)
{
Node *s = (Node *)malloc(sizeof(Node));
if (!s)
return FALSE;
s->data = e;
s->next = NULL;
Q->rear->next = s; // 把拥有元素e的新结点s赋值给原队尾结点的后继,见图中①
Q->rear = s; // 把当前的s设置为队尾结点,rear指向s,见图中②
return TRUE;
}
// 出队操作
Status deQueue(LinkQueue *Q, ElemType *e)
{
Node *p;
if (Q->front == Q->rear)
return FALSE;
p = Q->front->next; // 将欲删除的队头结点暂存给p,见图中①
*e = p->data; // 将欲删除的队头结点的值赋值给e
Q->front->next = p->next; // 将原队头结点的后继p->next赋值给头结点后继,见图中②
if (Q->rear == p) // 若队头就是队尾,则删除后将rear指向头结点,见图中③
Q->rear = Q->front;
free(p);
return TRUE;
}
// 遍历队列操作
Status tarverseQueue(const LinkQueue Q)
{
Node *p;
p = Q.front->next;
while (p)
{
printf("%d ", p->data);
p = p->next;
}
printf("\n");
return TRUE;
}
// 销毁队列操作
Status destroyQueue(LinkQueue *Q)
{
while (Q->front)
{
Q->rear = Q->front->next;
free(Q->front);
Q->front = Q->rear;
}
return TRUE;
}
// 清空队列操作
Status clearQueue(LinkQueue *Q)
{
Node *p;
Node *q;
Q->rear = Q->front;
p = Q->front->next;
Q->front->next = NULL;
while (p)
{
q = p;
p = p->next;
free(q);
}
return TRUE;
}
// 判断是否为空队列
Status isEmpty(const LinkQueue Q)
{
return Q.front == Q.rear ? TRUE : FALSE;
}
// 获得队头元素
Status getHead(const LinkQueue Q, ElemType *e)
{
Node *p;
if (Q.front == Q.rear)
return FALSE;
p = Q.front->next;
*e = p->data;
return TRUE;
}
// 获得队列的长度
int getLength(const LinkQueue Q)
{
int i = 0;
Node *p;
p = Q.front;
while (Q.rear != p)
{
i++;
p = p->next;
}
return i;
}
int main()
{
LinkQueue Q;
// 初始化队列
initQueue(&Q);
// 入队操作
for (int i = 0; i < 4; i++)
enQueue(&Q, i);
printf("入队操作(0、1、2、3)! \n\n");
// 出队操作
ElemType d;
deQueue(&Q, &d);
printf("删除的元素是%d \n\n", d);
// 遍历队列
printf("遍历队列: ");
tarverseQueue(Q);
printf("\n");
// 判断是否为空队列
printf("现在队列空否? %u (1:空 0:否)\n\n", isEmpty(Q));
// 获得队列的长度
printf("队列长度为: %d \n\n", getLength(Q));
// 获得队头元素
getHead(Q, &d);
printf("队头元素是%d \n\n", d);
return 0;
}
输出结果如下图所示:
参考:
《大话数据结构 - 第4章》 栈与队列
数据结构 - 链队列的实行(C语言)的更多相关文章
- 数据结构——链队列(linked queue)
/* linkedQueue.c */ /* 链队列 */ #include <stdio.h> #include <stdlib.h> #include <stdboo ...
- 数据结构 - 链栈的实行(C语言)
数据结构-链栈的实现 1 链栈的定义 现在来看看栈的链式存储结构,简称为链栈. 想想看栈只是栈顶来做插入和删除操作,栈顶放在链表的头部还是尾部呢?由于单链表有头指针,而栈顶指针也是必须的,那干吗不让它 ...
- 数据结构 - 顺序队列的实行(C语言)
数据结构-顺序队列的实现 1 顺序队列的定义 线性表有顺序存储和链式存储,队列作为一种特殊的线性表,也同样存在这两种存储方式.我们先来看队列的顺序存储结构. 队列的顺序储存结构:用数组存储队列,为了避 ...
- C语言数据结构-循环队列的实现-初始化、销毁、清空、长度、队列头元素、插入、删除、显示操作
1.数据结构-循环队列的实现-C语言 #define MAXSIZE 100 //循环队列的存储结构 typedef struct { int* base; //基地址 int _front; //头 ...
- C语言数据结构-链式队列的实现-初始化、销毁、清空、长度、队列头元素、插入、删除、显示操作
1.数据结构-链式队列的实现-C语言 typedef struct QNode { int data; struct QNode *next; }QNode,*QueuePtr; typedef st ...
- 【Java】 大话数据结构(7) 循环队列和链队列
本文根据<大话数据结构>一书,实现了Java版的循环队列.链队列. 队列:只允许在一端进行插入操作,而在另一端进行删除操作的线性表. 1.循环队列 队列的顺序储存结构:用数组存储队列,引入 ...
- javascript实现数据结构与算法系列:队列 -- 链队列和循环队列实现及示例
1 队列的基本概念 队列(Queue):也是运算受限的线性表.是一种先进先出(First In First Out ,简称FIFO)的线性表.只允许在表的一端进行插入,而在另一端进行删除. 队首(fr ...
- java与数据结构(8)---java实现链队列
链队列 实际上就是单链表,只是规定了删除在队头进行,添加在队尾进行. 链队列代码结构 package list.queue; public interface Queuable<T>; p ...
- C语言实现链队列的初始化&进队&出队
/*链表实现队列的一系列操作*/ #include<stdio.h> #include<stdlib.h> #define OK 1 #define ERROR 0 typed ...
随机推荐
- D广搜
<span style="color:#330099;">/* D - 广搜 基础 Time Limit:1000MS Memory Limit:30000KB 64b ...
- 聚合类新闻client产品功能点详情分析
产品功能点 功能 今日头条 百度新闻 鲜果 ZAKER 媒体订阅 × √ ★ ★ 个性化内容推荐 ★ √ × × 个性化订阅(RSS) × × ★ × 视频新闻 × × × × 评论盖楼 √ √ √ ...
- soapUI系列之—-05 JDBC Request & Xpath Match
一.配置JDBC Connection String 1. 以Oracle为例,要使用JDBC数据库就要先下一个 oracle JDBC的驱动,下载成功后把它放到soapUI安装目录下的 bin/e ...
- Selenium系列之--03【转】页面元素找不到问题的分析思路
如果在测试过程中遇到了NoSuchElementException 这个异常, 说明元素查找失败. Caused by: org.openqa.selenium.NoSuchElementExcept ...
- Hibernate也须要呵护——Hibernate的泛型DAO
众所周之.面向对象的基础是抽象.也能够说,抽象促使编程在不断发展. 对于数据库的訪问,以前写过HqlHelper.EFHelper.编写Spring+Hibernate框架下的应用.也相同离不了编写一 ...
- struts2 java.io.FileNotFoundException: http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd
xxx-validation.xml 文件里 java.io.FileNotFoundException: http://www.opensymphony.com/xwork/xwork-valid ...
- Hibernate基础-HelloWord
1. ORM :ORM (Object /Relation Mapping ): 对象/关系映射(理解) 1) ORM 主要解决对象 -关系的映射 2) .ORM的思想:将关系数据 ...
- 谈谈TensorFlow with CPU support or TensorFlow with GPU support(图文详解)
不多说,直接上干货! You must choose one of the following types of TensorFlow to install: TensorFlow with CPU ...
- MFC程序打开文件对话框出错的问题解决
前几天从网上下了个图像分析的mfc小程序,是VC6的 用VC6在本地编译生成都没问题.执行起来弹出一个未处理的错误,程序崩溃退出. 想起来原来遇到过打开文件对话框方面的问题,当时项目时间紧张未能深究. ...
- 【iOS系列】-UIImageView帧动画相关属性介绍
UIImageView帧动画相关属性介绍 1:相关属性: //An array of UIImage objects to use for an animation.存放UIImage对象,会按顺序显 ...