数据结构:3.栈和队列

1.概念

1).栈

  • 栈是一种先进后出、后进先出的数据结构
  • 队列时钟先进先出、后进后出的数据结构
  • 栈、队列、表的区别
    • 栈和队列是一种特殊的表状结构
    • 栈和队列只能在特定的位置插入和删除
    • 表可以在任意位置插入和删除
    • 栈顶:允许入栈和出栈的一端
    • 栈底:不允许入栈和出栈的一端
    • 栈针:指向栈顶位置的指针或下表
  • 栈的分类
    • 增栈:栈向高地址增长
    • 减栈:栈向低地址增长
    • 空栈:指针指向入栈位置
    • 满栈:指针指向栈顶位置
    • 分类:空增栈、满增栈、空减栈、满减栈
  • 入栈(压栈):将数据插入栈顶元素的位置
  • 出栈(弹栈):将数据从栈顶元素位置取出

2).队列

  • 队头:出队的一端
  • 队尾:入队的一端
  • 出队:数据从队列中取出
  • 入队:数据向队列中插入

2.顺序栈

下为顺序栈的创建,入栈,出栈,判断空栈和满栈,销毁栈,seqstack.c文件

cs 复制代码
#include"seqstack.h"

SeqStack_t *CreateSeqStack(int MaxLen)
{
	SeqStack_t *pTmpStack = NULL;

	pTmpStack = malloc(sizeof(SeqStack_t));
	if (NULL == pTmpStack)
	{
		perror("fail to malloc");
		return NULL;
	}
	
	pTmpStack->pData = malloc(MaxLen * sizeof(DataType));
	if (NULL == pTmpStack->pData)
	{
		perror("fail to malloc");
		return NULL;
	}

	pTmpStack->top = 0;
	pTmpStack->maxlen = MaxLen;

	return pTmpStack;
}

int DestroySeqStack(SeqStack_t **ppStack)
{
	free((*ppStack)->pData);
	free(*ppStack);
	*ppStack = NULL;

	return 0;
}

int IsEmptySeqStack(SeqStack_t *pStack)
{
	return pStack->top == 0 ? 1 : 0;
}

int IsFullSeqStack(SeqStack_t *pStack)
{
	return pStack->top == pStack->maxlen ? 1 : 0;
}

int PushSeqStack(SeqStack_t *pStack, DataType TmpData)
{
	if (IsFullSeqStack(pStack))
	{
		return -1;
	}

	pStack->pData[pStack->top] = TmpData;
	pStack->top++;

	return 0;
}

DataType PopSeqStack(SeqStack_t *pStack)
{
	if (IsEmptySeqStack(pStack))
	{
		return -1;
	}

	pStack->top--;

	return pStack->pData[pStack->top];
}

main.c

cs 复制代码
#include "seqstack.h"

int main(void)
{
	SeqStack_t *pseqstack = NULL;

	pseqstack = CreateSeqStack(5);
	
	PushSeqStack(pseqstack, 1);
	PushSeqStack(pseqstack, 2);
	PushSeqStack(pseqstack, 3);
	PushSeqStack(pseqstack, 4);
	PushSeqStack(pseqstack, 5);
	PushSeqStack(pseqstack, 6);

	while (!IsEmptySeqStack(pseqstack))	
	{
		printf("%d ", PopSeqStack(pseqstack));
	}
	printf("\n");

	DestroySeqStack(&pseqstack);
	
	return 0;
}

seqstack.h

cs 复制代码
#ifndef __SEQSTACK_H__
#define __SEQSTACK_H__
#include<stdio.h>
#include<stdlib.h>
typedef int DataType;
typedef struct seqstack
{
	DataType *pData;
	int top;
	int maxlen;
}SeqStack_t;
//创建顺序栈
extern SeqStack_t *CreateSeqStack(int MaxLen);
//入栈
extern int PushSeqStack(SeqStack_t *pStack, DataType TmpData);
//判断是否满栈
extern int IsFullSeqStack(SeqStack_t *pStack);
//判断是否空栈
extern int IsEmptySeqStack(SeqStack_t *pStack);
//出栈
extern DataType PopSeqStack(SeqStack_t *pStack);
//销毁栈
extern int DestroySeqStack(SeqStack_t **ppStack);

#endif

3.循环队列

下为链式栈的创建,入栈,出栈,判断空栈,销毁栈,linkseqstack.c文件

cs 复制代码
#include"linkstack.h"
Node_t *CreateEmptyLinkStack(void)
{
	Node_t *pTmpStack = NULL;
	pTmpStack = malloc(sizeof(Node_t));
	if(pTmpStack == NULL)
	{
		perror("fail to malloc");
		return NULL;
	}
	pTmpStack->pnext = NULL;
	return pTmpStack;
}
int IsEmptyLinkStack(Node_t *pHead)
{
	return pHead->pnext == NULL?1:0;
}
int PushLinkStack(Node_t *pHead,DataType TmpData)
{
	Node_t *pTmpStack = malloc(sizeof(Node_t));
	if(pTmpStack == NULL)
	{
		perror("fail to malloc");
		return -1;
	}
	pTmpStack->Data = TmpData;
	pTmpStack->pnext = pHead->pnext;
	pHead->pnext = pTmpStack;
	return 0;
}
DataType popLinkStack(Node_t *pHead)
{
	Node_t *pFreeStack = pHead->pnext;
	DataType a = 0;
	if(IsEmptyLinkStack(pHead))
		return -1;
	pHead->pnext = pFreeStack->pnext;
	a = pFreeStack->Data;
	free(pFreeStack);
	pFreeStack = NULL;
	return a;
}
int DestroyLinkStack(Node_t **ppHead)
{
	Node_t *pTmpStack = NULL;
	Node_t *pFreeStack = NULL;
	pTmpStack = pFreeStack = *ppHead;
	while(pTmpStack != NULL)
	{
		pFreeStack = pTmpStack;
		pTmpStack = pTmpStack->pnext;
		free(pFreeStack);
	}
	*ppHead = NULL;
}

main.c

cs 复制代码
#include"linkstack.h"
int main(void)
{
	Node_t *year = CreateEmptyLinkStack();
	PushLinkStack(year,1);
	PushLinkStack(year,3);
	PushLinkStack(year,5);
	PushLinkStack(year,7);
	PushLinkStack(year,9);
	//while(year->top != 0)
	while(!IsEmptyLinkStack(year))
		printf("%d ",popLinkStack(year));
	putchar('\n');
	printf("未销毁:%p\n",year);
	DestroyLinkStack(&year);
	printf("已销毁:%p\n",year);
	return 0;
}

linkstack.h

cs 复制代码
#ifndef __LINKSTACK_H__
#define __LINKSTACK_H__

#include<stdio.h>
#include<stdlib.h>

typedef int DataType;
typedef struct linkstack
{
	DataType Data;
	struct linkstack *pnext;
}Node_t;

Node_t *CreateEmptyLinkStack(void);
int IsEmptyLinkStack(Node_t *pHead);
int PushLinkStack(Node_t *pHead,DataType TmpData);
DataType popLinkStack(Node_t *pHead);
int DestroyLinkStack(Node_t **ppHead);

#endif

4.循环队列

下为循环队列的创建,入队,出队,判断空和满,销毁,seqqueue.c文件

cs 复制代码
#include"seqqueue.h"
SeqQueue_t *CreateSeqQueue(int len)
{
	SeqQueue_t *pNowQueue = malloc(sizeof(SeqQueue_t));
	pNowQueue->pData = malloc((len+1)*sizeof(DataType));
	if(pNowQueue == NULL)
	{
		perror("fail to malloc");
		return NULL;
	}
	if(pNowQueue->pData == NULL)
	{
		perror("fail to malloc");
		return NULL;
	}
	pNowQueue->Head = pNowQueue->Tail = 0;
	pNowQueue->MaxLen = len;
	return pNowQueue;
}
int IsFullSeqQueue(SeqQueue_t *pTmpQueue)
{
	return ((pTmpQueue->Tail+1)%(pTmpQueue->MaxLen+1) == pTmpQueue->Head)?1:0;
}
int IsEmptySeqQueue(SeqQueue_t *pTmpQueue)
{
	return (pTmpQueue->Tail == pTmpQueue->Head)?1:0;
}
int EnterSeqQueue(SeqQueue_t *pTmpQueue,DataType TmpData)

{
	if(IsFullSeqQueue(pTmpQueue))
		return -1;
	pTmpQueue->pData[pTmpQueue->Tail] = TmpData;
	TmpData = pTmpQueue->pData[pTmpQueue->Head];
	pTmpQueue->Tail = (pTmpQueue->Tail+1)%(pTmpQueue->MaxLen+1);
	return 0;
}
DataType QuitSeqQueue(SeqQueue_t *pTmpQueue)
{
	DataType TmpData;
	if(IsEmptySeqQueue(pTmpQueue))
		return -1;
	TmpData = pTmpQueue->pData[pTmpQueue->Head];
	pTmpQueue->Head = (pTmpQueue->Head+1)%(pTmpQueue->MaxLen+1);
	return TmpData;
}
int DestroySeqQueue(SeqQueue_t **ppTmpQueue)
{
	free((*ppTmpQueue)->pData);
	free(*ppTmpQueue);
	*ppTmpQueue = NULL;
	return 0;
}

main.c

cs 复制代码
#include"seqqueue.h"
int main(void)
{
	SeqQueue_t *shi = CreateSeqQueue(12);
	int a = 1;
	
	printf("%d \n",IsFullSeqQueue(shi));
	while(!IsFullSeqQueue(shi))
	{
		EnterSeqQueue(shi,a);
		a++;
	}
	putchar('\n');
	while(!IsEmptySeqQueue(shi))
		printf("%d ",QuitSeqQueue(shi));
	putchar('\n');
	printf("%p\n",shi);
	DestroySeqQueue(&shi);
	printf("%p\n",shi);
	return 0;
}

seqqueue.h

cs 复制代码
#ifndef __SEQQUEUE_H__
#define __SEQQUEUE_H__

#include<stdio.h>
#include<stdlib.h>

typedef int DataType;
typedef struct queue
{
	DataType *pData;
	int Head;            //头下标
	int Tail;            //尾下标
	int MaxLen;
}SeqQueue_t;

extern SeqQueue_t *CreateSeqQueue(int len);
extern int IsEmptySeqQueue(SeqQueue_t *pTmpQueue);
extern int IsFullSeqQueue(SeqQueue_t *pTmpQueue);
extern int EnterSeqQueue(SeqQueue_t *pTmpQueue,DataType TmpData);
extern DataType QuitSeqQueue(SeqQueue_t *pTmpQueue);
extern int DestroySeqQueue(SeqQueue_t **ppTmpQueue);

#endif

5.链式队列

下为链式队列的创建,入队,出队,判断是否为空,销毁,linkstack.c文件

cs 复制代码
#include"linkqueue.h"
Node_t *CreateLinkQueue(void)
{
	Node_t *pTmpQueue = malloc(sizeof(Node_t));
	if(pTmpQueue == NULL)
	{
		perror("fail to malloc");
		return NULL;
	}
	pTmpQueue->pNext = NULL;
	return pTmpQueue;
}
int IsEmptyLinkQueue(Node_t *pTmpQueue)
{
	return (pTmpQueue->pNext == NULL)?1:0;
}
int EnterLinkQueue(Node_t *pTmpQueue,DataType TmpData)
{
	Node_t *pNowQueue = malloc(sizeof(Node_t));;
	if(pNowQueue == NULL)
	{
		perror("fail to malloc");
		return -1;
	}
	Node_t *pLastQueue = pTmpQueue;
	while(pLastQueue->pNext != NULL)
	{
		pLastQueue = pLastQueue->pNext;
	}
	pNowQueue->Data = TmpData;
	pNowQueue->pNext = pLastQueue->pNext;//NULL
	pLastQueue->pNext = pNowQueue;
	return 0;
}
DataType QuitlinkQueue(Node_t *pTmpQueue)
{
	DataType TmpData;
	Node_t *pFreeNode = pTmpQueue->pNext;
	if(IsEmptyLinkQueue(pTmpQueue))
		return -1;
	pTmpQueue->pNext = pFreeNode->pNext;
	TmpData = pFreeNode->Data;
	free(pFreeNode);
	pFreeNode = NULL;
	return TmpData;

}
int DestroyLinkQueue(Node_t **ppTmpQueue)
{
	Node_t *pTmpQueue = *ppTmpQueue;
	Node_t *pFreeNode = *ppTmpQueue;
	while(pTmpQueue != NULL)
	{
		pTmpQueue = pFreeNode->pNext;
		free(pFreeNode);
		pFreeNode = pTmpQueue;
	}
	*ppTmpQueue = NULL;
	return 0;
}

main.c

cs 复制代码
#include"linkqueue.h"
int main(void)
{
	Node_t *year = CreateLinkQueue();
	DataType a = 12;
	while(a!=0)
	{
		EnterLinkQueue(year,a);
		a-=2;
	}putchar('\n');
	while(!IsEmptyLinkQueue(year))
	{
		printf("%d ",QuitlinkQueue(year));
	}
	putchar('\n');
	printf("%p\n",year);
	DestroyLinkQueue(&year);
	printf("%p\n",year);
	return 0;
}

linkstack.h

cs 复制代码
#ifndef __LINKQUEUE_H__
#define __LINKQUEUE_H__

#include<stdio.h>
#include<stdlib.h>

typedef int DataType;
typedef struct node
{
	DataType Data;
	struct node *pNext;
}Node_t;
extern Node_t*CreateLinkQueue(void); 
extern int IsEmptyLinkQueue(Node_t *pTmpQueue);
extern int EnterLinkQueue(Node_t *pTmpQueue,DataType TmpData);
extern DataType QuitlinkQueue(Node_t *pTmpQueue);
extern int DestroyLinkQueue(Node_t **ppTmpQueue);


#endif
相关推荐
梵刹古音2 小时前
【C语言】 递归函数
c语言·数据结构·算法
代码游侠3 小时前
C语言核心概念复习(二)
c语言·开发语言·数据结构·笔记·学习·算法
you-_ling3 小时前
数据结构:5.哈希表
数据结构·散列表
鲨辣椒100864 小时前
二叉树代码变现——递归函数实现深度遍历
数据结构
2301_810730104 小时前
python第四次作业
数据结构·python·算法
春栀怡铃声4 小时前
认识二叉树~
c语言·数据结构·经验分享·c·编译
仰泳的熊猫4 小时前
题目1434:蓝桥杯历届试题-回文数字
数据结构·c++·算法·蓝桥杯
ygklwyf5 小时前
模拟退火算法零基础快速入门
数据结构·c++·算法·模拟退火算法
寄存器漫游者5 小时前
数据结构 二叉树与哈希表
数据结构·散列表