[C语言实现]数据结构——手撕顺序栈之我出生就会写一个栈

news2025/1/11 12:55:11


🥰作者: FlashRider

🌏专栏: 数据结构


目录

栈的前置知识

1.什么是栈?

2.生活中哪些地方有栈的影子?

顺序表实现栈

1.为什么通常采用顺序表实现栈?

2.栈的实现



栈的前置知识

1.什么是栈?

栈(stack)又名堆栈,它是一种运算受限的线性表。限定仅在表尾进行插入和删除操作的线性表。这一端被称为栈顶,相对地,把另一端称为栈底。向一个栈插入新元素又称作进栈、入栈或压栈,它是把新元素放到栈顶元素的上面,使之成为新的栈顶元素;从一个栈删除元素又称作出栈或退栈,它是把栈顶元素删除掉,使其相邻的元素成为新的栈顶元素。

总的来说,栈就是一个线性表,只不过只能从栈顶入栈,也只能从栈顶出栈,因此栈有一个非常重要的特性——后进先出(First In Last Out)。

2.生活中哪些地方有栈的影子?

让我们来看看下面这段代码:

void f()
{
    printf("666\n");
}
int main()
{
    printf("777\n");
    f();
    return 0;
}

程序的入口是main函数, 然后执行了printf函数,printf函数结束,然后执行f()函数,在f()函数中执行了第二个printf函数,然后第二个printf函数结束,随后f()函数结束,最后才是main函数结束。

我们可以发现,作为程序入口的main反而是最后结束的,而越后执行的函数越先结束,这就是栈的后进先出特性。所以函数就是利用栈来实现调用的。

 然后printf   f()    main再依次出栈,程序结束。


顺序表实现栈

1.为什么通常采用顺序表实现栈?

我们可以发现,对栈进行插入和删除操作时,永远是在栈顶进行操作,我们把栈顺时针旋转90°,
就变成了只在表尾插入删除的线性表,因为不会大量挪动元素,所以我们选择顺序表实现。

2.栈的实现

头文件 Stack.h

#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <assert.h>
typedef int STDataType;
typedef struct Stack
{
    STDataType* a;//存放数据的空间首地址
    int capacity;//当前栈最大容量
    int top;//模拟栈顶指针
}ST;
//初始化栈
void StackInit(ST* ps);
//销毁栈 
void StackDestroy(ST* ps);
//插入
void StackPush(ST* ps, STDataType x);
//弹出 
void StackPop(ST* ps);
//获取栈顶元素
STDataType GetTop(ST* ps);
//获取栈当前元素个数
int StackSize(ST* ps);
//判断栈是否为空
bool StackEmpty(ST* ps);

源文件 Stack.c 

//初始化栈
void StackInit(ST* ps)
{
	assert(ps);
	ps->a = NULL;
	ps->capacity = ps->top = 0; 
}
//销毁栈 
void StackDestroy(ST* ps)
{
	assert(ps);
	free(ps->a);
	ps->a = NULL;
	ps->capacity = ps->top = 0;
}
//插入
void StackPush(ST* ps, STDataType x)
{
	assert(ps);
	//判满 
	if(ps->capacity == ps->top)
	{
		int newcapacity = ps->capacity == 0 ? 4 : ps->capacity * 2;
		STDataType* tmp = (STDataType*)realloc(ps->a, sizeof(STDataType) * newcapacity);
		if(tmp == NULL)
		{
			printf("malloc fail\n");
			exit(-1);
		}
		ps->a = tmp;
		ps->capacity = newcapacity;
	}
	//插入元素 
	ps->a[ps->top++] = x;
}
//弹出 
void StackPop(ST* ps)
{
	assert(ps);
	assert(!StackEmpty(ps));
	ps->top--;
}
//获取栈顶元素
STDataType GetTop(ST* ps)
{
	assert(ps);
	assert(!StackEmpty(ps));
	return ps->a[ps->top - 1];
}
//获取栈当前元素个数
int StackSize(ST* ps)
{
	assert(ps);
	return ps->top;
}
//判断栈是否为空
bool StackEmpty(ST* ps)
{
	assert(ps);
	return ps->top == 0;
}

测试一下写出来的栈是否可用

源文件 test.c

int main()
{
	Stack st;
	StackInit(&st);
	StackPush(&st, 1);	
	StackPush(&st, 2);
	StackPush(&st, 3);
	StackPush(&st, 4);
	StackPush(&st, 5);
	while(!StackEmpty(&st))
	{
		printf("%d ", GetTop(&st));
		StackPop(&st);
	}
	return 0;
}

结果:


 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/627599.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

spring实例化bean属性填充

实例化bean之后要执行属性填充&#xff0c;也就是serviceA注入了servcieB&#xff0c;实例化servcieA时要通过populateBean先实例化serviceB. 也就是最终要执行serviceB的getBean 只是字段注入的流程 关键的两个Processor AutowiredAnnotationBeanPostProcessor 处理Autowire…

Databend 开源周报第 96 期

Databend 是一款现代云数仓。专为弹性和高效设计&#xff0c;为您的大规模分析需求保驾护航。自由且开源。即刻体验云服务&#xff1a;https://app.databend.cn 。 Whats On In Databend 探索 Databend 本周新进展&#xff0c;遇到更贴近你心意的 Databend 。 虚拟列 查询 J…

Angular与PDF之四: 反思代码与模板的复用

在我们前面关于Angular与PDF的几篇博客中分别讲了如何在在如何在客户端渲染PDF(Angular与PDF之一&#xff1a;如何在客户端渲染PDF_angular pdf_KenkoTech的博客-CSDN博客) 和预览&#xff08;Angular 与PDF之二&#xff1a;打印预览的实现_angular pdf预览_KenkoTech的博客-CS…

Easeui 02 tree组件.

1.添加tree组件. tree组件的位置&#xff1a;DataGrid and Tree(表格和树) → tree(树)&#xff1b; 复制 tree组件到 "菜单管理"的div里面&#xff0c;如&#xff1a; 这里要动态绑定数据&#xff0c;所以把死数据删除&#xff0c;只留下一个 ul&#xff0c;如&am…

HCIA-动态路由

目录 动态路由&#xff1a; 动态路由的分类 按工作区域分类&#xff1a; 按算法和工作机制分类&#xff1a; 距离矢量路由协议&#xff1a; 链路状态路由协议&#xff1a; OSPF协议计算路由步骤&#xff1a; OSPF协议 OSPF协议报文&#xff1a; OSPF三张表 OSPF路由…

算法修炼之筑基篇——筑基一层后期(解决KMP算法,KMP算法模板)

✨博主&#xff1a;命运之光​​​​​​ &#x1f984;专栏&#xff1a;算法修炼之练气篇​​​​​ &#x1f353;专栏&#xff1a;算法修炼之筑基篇 ✨博主的其他文章&#xff1a;点击进入博主的主页​​​​​​ 前言&#xff1a;学习了算法修炼之练气篇想必各位蒟蒻们的基…

kafka 四 Kafka读写流程、LEO log end offset、物理存储 稠密索引 稀疏索引 、Kafka物理存储、深入了解读数据流程、删除消息

目录 Kafka读写流程 LEO log end offset 物理存储 稠密索引 稀疏索引 Kafka物理存储 深入了解读数据流程 删除消息 Kafka读写流程 写流程&#xff1a; 通过zookeeper 找leader分配开始读写Isr中的副本同步数据&#xff0c;并返回给leader ack返回给 分片ack 读流程&…

2023高考语文,用ChatGPT挑战全国卷作文,已达到双一流高校学生水平?

前言 2023年高考语文结束啦&#xff0c;今天我们用ChatGPT来挑战高考作文&#xff0c;一起来看看它的表现如何&#xff1f;ChatGPT突然爆火网络&#xff0c;它真的会取代人类的工作吗&#xff1f; 什么是ChatGPT&#xff1f; ChatGPT是由OpenAI开发的&#xff0c;OpenAI是一家…

BBA EDI 项目数据库方案开源介绍

近期为了帮助广大用户更好地使用 EDI 系统&#xff0c;我们根据以往的项目实施经验&#xff0c;将成熟的 EDI 项目进行开源。用户安装好知行之桥EDI系统之后&#xff0c;只需要下载我们整理好的示例代码&#xff0c;并放置在知行之桥指定的工作区中&#xff0c;即可开始使用。 …

排序算法的复杂度及稳定性详解(内含记忆小窍门)

排序算法的复杂度及稳定性 一、排序算法分类二、概念2.1 时间复杂度2.2 空间复杂度2.3 稳定性 三、表格比较注意 四、部分排序分析4.1 直接插入排序图示代码 4.2 冒泡排序图示代码 4.3 快速排序图示代码 五、结构化记忆&#xff08;小窍门&#xff09;5.1 结构化5.2 我的结构化…

2023 如何备考系统架构师?

高级系统架构设计师难度还是有的&#xff0c;所以一般千万不要裸考&#xff01;&#xff01;要时间充足&#xff0c;至少要接触过&#xff0c;反正没有基础的尽量还是不要去裸考了&#xff01; 一、系统架构设计师考试题型 考试科目分为综合题&#xff08;选择题&#xff09;&a…

Stable Diffusion最全保姆级安装教程(建议收藏)

Midjourney 因细致的画图风格备受大家的欢迎&#xff0c;但由于其网络环境以及会员费&#xff0c;导致入门门槛过高&#xff0c;拦住了很多对AIGC感兴趣的小伙伴。 今天阿良就教大家&#xff0c;不需要魔法&#xff0c;也不用交会员费&#xff0c;尽情玩转AI出图的保姆级安装教…

力扣算法系统刷题详细题解记录二(字符串、双指针法、栈与队列)

力扣算法系统刷题题解记录二&#xff08;字符串、双指针法、栈与队列&#xff09; 前言 参考顺序和资料&#xff1a;《代码随想录》 二刷要认真做笔记啦&#xff0c;加油&#xff01; 笔记模板&#xff1a; #### 解题思路#### 示意图#### 代码四、字符串 344.字符串反转 编…

求最小生成树(Kruskal算法和Prim算法)

目录 一、前言 二、相关概念 1、最小生成树 2、Prim算法&#xff08;对结点进行操作&#xff09; 3、kruskal 算法&#xff08;对边进行操作&#xff09; 三、例题 1、修建公路&#xff08;lanqiaoOJ题号1124&#xff09; 1、Prim算法题解 2、Kruskal算法 一、前言 很…

PyToch 深度学习 || 卷积神经网络分类

卷积神经网络分类 import torch import torch.nn as nn import torchvision import numpy as np from torch.autograd import Variable import matplotlib.pyplot as plt import torch.nn.functional as F import torch.utils.data as Data from torchvision import datasets,…

【业务功能篇20】Springboot java逻辑实现动态行转列需求

在此前&#xff0c;我也写过一个行转列的文章&#xff0c;是用存储过程sql处理的一个动态的逻辑 Mysql 存储过程\Mybatis框架call调用 实现动态行转列 那么后面我们同样又接收了业务的一个新需求&#xff0c;针对的是不同的业务数据&#xff0c;做的同样的一个展示数据报表&…

【C++11】 initializer_list | 右值引用 | 移动构造 | 完美转发

文章目录 1. 统一的列表初始化{ } 初始化initializer_list 2. 引用左值引用右值引用左值引用与右值引用的相互转换右值引用的真正使用场景移动构造 C98与C11传值返回问题注意事项总结 3. 完美转发 1. 统一的列表初始化 { } 初始化 C11 扩大了括号括起的列表(初始化列表)的使用…

使用PHP导出Excel时处理复杂表头的万能方法

使用PHP导出Excel时&#xff0c;如果是一级表头处理起来很简单&#xff0c;但如果碰到复杂一点的表头&#xff0c;比如二级、三级&#xff0c;甚至更多级别的表头要怎么办呢&#xff1f; 就像下面这个表头&#xff0c;有三层&#xff0c;并且每层都不太规则—— 难道我们每次处…

动态绑定v-model,并解决输入框无法输入和无法双向绑定问题

问题&#xff1a;在界面中想要动态获取数据库中返回的数据&#xff0c;作为下拉的值&#xff0c;每个下拉值中又包含不同的属性信息&#xff0c;给输入框动态绑定v-model&#xff0c;但是绑定成功后输入框内无法输入内容&#xff0c;且没有双向绑定 解决思路&#xff1a;1.双向…

SIM:基于搜索的用户终身行为序列建模

SIM&#xff1a;基于搜索的用户终身行为序列建模 论文&#xff1a;《Search-based User Interest Modeling with Lifelong Sequential Behavior Data for Click-Through Rate Prediction》 下载地址&#xff1a;https://arxiv.org/abs/2006.05639 1、用户行为序列建模回顾 1…