【数据结构】基础:栈(C语言)
摘要:本文主要介绍栈的特性以及分析如何实现并实现栈这一数据结构
一、概述
栈是一种特殊的线性表,其只允许在固定的一端进行插入和删除元素操作,进行数据插入和删除操作的一端称为栈顶,另一端称为栈底。栈中的数据元素遵守后进先出LIFO(Last In First Out)的原则。
压栈:栈的插入操作叫做进栈/压栈/入栈,入数据在栈顶。
出栈:栈的删除操作叫做出栈。出数据也在栈顶。
示意图如下:
二、分析
在实现栈之前,先对其进行分析,特别是用什么数据结构,什么形式进行书写。对于栈的概述中可以发现,栈时线性结构,可以通过顺序表的形式,或者链表的形式进行书写。从实现上,如果使用链表书写,需要进行指针的各种定向,使用顺序表,只需要使用下标,就可以完成操作。对于实现困难程度而言,其实顺序表是更加简单的,只是在开辟空间时需要注意,但两种实现方式都是需要开辟空间的,因此本文使用顺序表对其实现。
在实现之前,对栈进行定义,由于是顺序表,可以通过一个指针与一个容量参数进行空间开辟与判断是否开辟空间,再有一个参数表示栈顶。实现代码如下:
typedef int StackDataType;
struct Stack {
StackDataType* arrStack;
size_t top;
size_t capacity;
};
typedef struct Stack Stack;
三、实现
3.1 初始化
对于初始化操作,只需要进行开辟空间并修改对应参数即可。
void StackInit(Stack* stack) {
assert(stack);
StackDataType* ptemp = (StackDataType*)malloc(sizeof(StackDataType) * 4);
if (ptemp == NULL) {
perror("malloc failed!");
exit("-1");
}
stack->arrStack = ptemp;
stack->top = 0;
stack->capacity = 4;
}
3.2 销毁
对于销毁实现,将在堆区开辟的空间销毁并且设置参数为最初始化。
void StackDestory(Stack* stack) {
assert(stack);
stack->capacity = 0;
stack->top = 0;
free(stack->arrStack);
}
3.3 入栈
入栈之前,需要注意的是是否需要顺序表进行扩容,如果需要扩容就要再向堆区开辟空间并且修改容量数据,否则会出现越界的问题。判断之后,通过下标赋值,并修改栈顶位置。
void StackPush(Stack* stack, StackDataType val) {
assert(stack);
if (stack->top == stack->capacity) {
StackDataType* ptemp =
(StackDataType*)realloc(stack->arrStack,sizeof(StackDataType) * stack->capacity * 2);
if (ptemp == NULL) {
perror("realloc failed!");
exit(-1);
}
stack->capacity = stack->capacity * 2;
stack->arrStack = ptemp;
}
stack->arrStack[stack->top] = val;
stack->top++;
}
3.4 出栈
对于出栈,和入栈一样需要对其栈是否有元素进行判断,此处使用断言处理,而出栈就是修改栈顶位置,因为只能通过栈顶以后的元素,当访问后,会对原数据进行覆盖。
void StackPop(Stack* stack) {
assert(stack);
assert(stack->top != 0);
stack->top--;
}
3.5 获取栈顶数据
此处栈顶top表示栈的元素个数,但数组访问需要对栈顶位置减一,最后下标访问即可
StackDataType StackTop(Stack* stack) {
assert(stack);
return stack->arrStack[stack->top - 1];
}
3.6 判空
查看栈顶位置是否为零即可
int isStackEmpty(Stack* stack) {
assert(stack);
return stack->top == 0;
}
3.7 求大小
此处设计top就是栈中元素个数
int StackSize(Stack* stack) {
assert(stack);
return stack->top;
}
补充:
- 代码将会放到:C_C++_REVIEW: 一套 C/C++ 系统完整的使用手册,以及部分疑难杂症的解析 (gitee.com) ,欢迎查看!
- 欢迎各位点赞、评论、收藏与关注,大家的支持是我更新的动力,我会继续不断地分享更多的知识!