数据结构——栈(Stack)

目录

1.栈的介绍

2.栈工程

2.1 栈的定义

2.1.1 单链表实现栈

2.1.2 数组实现栈

2.1.2.1 静态数组栈

2.1.2.2 动态数组栈

2.2 栈的函数接口

2.2.1 栈的初始化

2.2.2 栈的数据插入(入栈)

2.2.3 栈的数据删除(出栈)

2.2.4 判断栈是否为空

2.2.5 取栈顶数据

2.2.6 栈数据统计

2.2.7 栈销毁

3. 栈总结反思


1.栈的介绍

        栈这个东西我们并不陌生,有过一些基础知识的同志都知道,在存储器映像中就有一块存储区域被称为栈。这个栈主要是存储非静态局部变量,函数调用所开辟出的栈帧也在这块区域。对于这块区域,我们很明确的一点就是它的特征:先进后出,后进先出。在程序运行时(以Linux+IA32为例),栈顶指针esp在面对push和pop指令时会对应的减或加,栈空间的开辟和释放都是由esp指针来标定的。所以可以看到在栈区内,当要完成空间释放或申请时,总是在对最顶部的空间进行操作,即满足“先进后出,后进先出”的规则。

        我们今天要介绍的栈则是一种数据结构,也属于线性表的一种,其重要特征就是我们刚才所提到的先进后出,后进先出。当数据存入时,会采取push(入栈/压栈)操作,将数据存储在栈顶;当数据删除时,会采取pop(出栈/弹栈)操作,将位于栈顶位置的数据删除。

2.栈工程

2.1 栈的定义

        在实现栈的时候,我们需要考虑数据存储的方式。我们到目前掌握的存储方式有如顺序表的数组的结构,除此之外,还有链表结构。在实现栈这一方面,链表和数组的方式存储都可以。但是考虑到我们在需要频繁地访问栈顶,我们需要对这两种方式有所规定。

2.1.1 单链表实现栈

        使用单链表的时候我们要规定好栈顶和栈底。因为对于栈这种数据结构,我们需要频繁地访问栈顶,但是对于单链表而言其数据的插入是将结点链接在链表末端。两相对比,我们发现使用单链表在入栈出栈的时候代价很大,需要遍历链表。所以我们一般不使用单链表来实现栈。

2.1.2 数组实现栈

        使用数组实现栈也同样需要先明确栈顶栈底的位置。因为栈顶是“灵活多变”的,栈顶会随着数据的插入和删除而更改位置。对于一个数组而言很明显下标大的一端更容易适应这样的特性,所以我们一般将下标为0的一端作为栈底,将下标较大的一端作为栈顶。

        在明确了数组的格式后,我们自然的想到动态的数组和静态的数组两种结构。

2.1.2.1 静态数组栈

        对于一个静态数组栈,其数组长度是定长的,我们定义一个常量来统一管理。其栈结构(结构体)中除了一个存储数据的定长数组之外,还应该有一个成员来标识栈顶的位置,便于我们对栈进行访问。

//静态
typedef int STDataType;
#define N 10
typedef struct Stack
{STDataType _a[N];int _top; // 栈顶
}Stack;
2.1.2.2 动态数组栈

        对于动态数组的栈来说,为满足其灵活管理空间的功能,其结构体内需要一个指针指向我们动态开辟的数组。同样的我们也需要一个成员标识栈顶位置,还需要一个成员存储数组容量上限。

typedef int STDataType;typedef struct Stack
{STDataType* data;int top;int capacity;
}ST;

2.2 栈的函数接口

2.2.1 栈的初始化

        当新建一个栈后,我们需要对其结构体进行初始化。将指针值为空,将容量初始化为0,同时将表示栈顶的成员置为-1。top初始化为-1,表示栈顶所在元素下标,-1即为栈为空。也可以将top初始化为0,表示栈内元素个数。此处选择第一种方式。

void STInit(ST* pst)
{assert(pst);pst->data = NULL;pst->top = -1;pst->capacity = 0;
}

2.2.2 栈的数据插入(入栈)

        当要在栈中插入数据时,我们首先要判断是否需要扩容,从而防止越界访问的问题。修改完容量后只需要将数据存储到数组的末端(栈顶)即可。

void STPush(ST* pst,STDataType x)
{assert(pst);if (pst->top + 1 == pst->capacity){int newcapacity = pst->capacity == 0 ? 4 : pst->capacity * 2;STDataType* tmp = realloc(pst->data, newcapacity*sizeof(STDataType));if (tmp == NULL){perror("realloc fail");return;}pst->data = tmp;pst->capacity = newcapacity;}pst->top++;pst->data[pst->top] = x;
}

2.2.3 栈的数据删除(出栈)

        出栈只需要将top减1即可,注意使用断言限制空指针与越界访问。

void STPop(ST* pst)
{assert(pst);assert(pst->top != -1);pst->top--;
}

2.2.4 判断栈是否为空

        栈是否为空只需要判断top成员是否为-1即可。

bool STEmpty(ST* pst)
{assert(pst);return pst->top == -1;
}

2.2.5 取栈顶数据

        因为top保存的是栈顶的下标,所以取栈顶元素只需要访问该下标元素即可。

STDataType STTop(ST* pst)
{assert(pst);assert(pst->top != -1);return pst->data[pst->top];
}

2.2.6 栈数据统计

        该接口是为了输出此时栈内的数据个数,只需将栈顶下标加一即可。

int STSize(ST* pst)
{assert(pst);return pst->top + 1;
}

2.2.7 栈销毁

        销毁栈需要将其数组空间释放,并将结构体内成员值全部初始化。

void STDestroy(ST* pst)
{assert(pst);free(pst->data);pst->data = NULL;pst->capacity = 0;pst->top = -1;
}

3. 栈总结反思

        栈主要实现了“先进后出,后进先出”的特殊功能,这就意味着栈这种数据结构在面对一些满足该特性的一些特殊情况下才能很好的适配。其结构和实现并不复杂,相较于其他数据结构很容易理解,特征也非常明显,处理好一些类似于下标之类的小细节就没问题了。

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

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

相关文章

每日一题——LeetCode1160.拼写单词

方法一 个人方法: 先统计chars里每个字符出现的次数,再对words里每个字符串统计每个字符出现的字符,当: 1、字符串里出现chars里没有的字符 2、字符串里某个字符出现的次数大于该字符在chars里出现的次数 以上两种情况则不符合…

基于微信小程序的音乐平台 开源项目

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、功能模块三、系统展示 四、核心代码4.1 查询单首音乐4.2 新增音乐4.3 新增音乐订单4.4 查询音乐订单4.5 新增音乐收藏 五、免责说明 一、摘要 1.1 项目介绍 基于微信小程序JAVAVueSpringBootMySQL的音乐平台,包含了音乐…

【MIT 6.S081】2020, 实验记录(3),Lab: page tables

目录 TaskTask 1: Print a page table Task Task 1: Print a page table 该实验需要增加一个 vmprint 函数,用于打印一个 page table,实现过程可以参考 vm.c 文件中的 freewalk() 函数。 在 defs.h 中增加 vmprint 的定义: void …

宝塔安装redis并且远程连接redis教程

第一步:搜索redis并安装 第二步:在防火墙添加端口6379 第三步:查看宝塔防火墙是否开启了6379端口 firewall-cmd --zonepublic --list-ports 很显然并没有开启 第四步:开启防火墙的6379端口 firewall-cmd --zonepublic --add-po…

【python】搭配Miniconda使用VSCode

现在的spyder总是运行出错,启动不了,尝试使用VSCode。 一、在VSCode中使用Miniconda管理的Python环境,可以按照以下步骤进行: a. 确保Miniconda环境已经安装并且正确配置。 b. 打开VSCode,安装Python扩展。 打开VS…

linux软件安装(yum命令)

1.Linux系统的应用商店 操作系统安装软件有许多种方式,一般分为: 下载安装包自行安装 如win系统使用exe文件、msi文件等如mac系统使用dmg文件、pkg文件等 系统的应用商店内安装 如win系统有Microsoft Store商店如mac系统有AppStore商店 Linux命令行…

qt学习:多界面跳转+信号+槽函数

目录 概念 分类 多界面编程思路 新建界面 注意 头文件 无数据传输跳转界面 有数据传输跳转界面 对象公有接口 界面之间数据传输 信号与槽函数进行数据传输跳转界面 信号: 槽: 概念 格式1 关联信号和发送信号 格式2 通信步骤 自定义信号和槽函数 总结 实…

精彩手绘全解:RAG技术,从入门到精通

本文整理自IVAN ILIN发布于Towards AI的博客[1]。感谢作者的精彩讲解。 深度学习自然语言处理 分享整理:Winnie 引言 检索增强生成(Retrieval Augmented Generation,简称RAG)为大型语言模型(LLMs)提供了从某…

绘图工具用的好,头发掉的少

程序员不管是在学习,还是工作过程中,很多时候都需要画图,如产品分析、架构设计、方案选型等,良好的绘图不仅可以让绘图者的思路清晰,也可以让聆听者更好的理解。用好画图,升职加薪少不了!今天介…

C程序训练:与输入有关的错误

在录入程序时有时稍不注意就可能录入错误的字符导致程序运行结果出现错误&#xff0c;下面举例说明。 下面程序的运行结果是错的&#xff0c;但程序又没有错&#xff0c;到底问题出现在哪呢&#xff1f; #include <stdio.h> int main() {FILE *fp;int i, k, n;fpfopen(…

OceanBase 4.2特性解读:Show Trace全链路跟踪,助力快速问题定位与精准诊断

在分布式数据库环境下&#xff0c;慢 SQL 诊断是运维人员面临的一大挑战。在无法及时发现问题根本原因的情况下&#xff0c;可能会严重影响用户体验&#xff0c;甚至会导致业务服务不可用。相对于单机数据库&#xff0c;分布式数据库系统涉及多个节点、多组件的协同工作&#x…

Go语言认识

Go语言认识 1. Go语言的设计背景2. Go语言的历程3. Go语言对比分析4. Go语言未来的发展规划5. 要不要选择Go 关注 go博客 直接了解第一手资料。 go文档 了解go的全貌。 1. Go语言的设计背景 Go语言&#xff08;也称为Golang&#xff09;是由Google开发的一种编程语言。它的设计…

构建基于RHEL7(CentOS7)的OpenSSH9.5p1的RPM包和升级回退方案

本文适用&#xff1a;RHEL7系列&#xff0c;或同类系统(CentOS7等) 文档形成时期&#xff1a;2023年 因软件世界之复杂和个人能力之限&#xff0c;难免疏漏和错误&#xff0c;欢迎指正。 文章目录 环境准备安装依赖openssh-9.5p1-el7.spec内容构建RPM包下载安装前注意事项开启t…

SQL注入攻击

1.用java实现登录的检查 package jdbc1;import java.sql.Connection; import java.sql.DriverManager; import java.sql.ResultSet; import java.sql.Statement; import java.util.Scanner;public class Login {public static void main(String args[]){try(Connection connec…

Redis管道操作

文章目录 1. 问题提出2. 解决方案3. 案例演示4. 总结 1. 问题提出 如何优化频繁命令往返造成的性能瓶颈&#xff1f; Redis是一种基于C/S一级请求响应协议的TCP服务&#xff0c;一个请求会遵循一下步骤&#xff1a; 客户端向服务端发送命令分四步&#xff08;发送命令-> …

教程视频二维码怎么做?扫码学习使用技巧

现在购买商品时经常会发现使用手册或者包装上会印有相关的二维码&#xff0c;扫码可以查看产品介绍或者使用说明的视频教学。将需要展示的内容放到二维码中&#xff0c;让用户能够通过扫码了解内容详情&#xff0c;有效的降低成本而且方便用户获取内容。 那么如果想要制作视频…

中科星图——Landsat9_C2_SR大气校正后的地表反射率数据

数据名称&#xff1a; Landsat9_C2_SR 数据来源&#xff1a; USGS 时空范围&#xff1a; 2022年1月-2023年3月 空间范围&#xff1a; 全国 数据简介&#xff1a; Landsat9_C2_SR数据集是经大气校正后的地表反射率数据&#xff0c;属于Collection2的二级数据产品&#…

128基于matlab的粒子群优化算法寻找多元函数的最大值

基于matlab的粒子群优化算法寻找多元函数的最大值&#xff0c;可定义多元函数&#xff0c;变量区间范围&#xff0c;输出最大值条件下的变量值。程序已调通&#xff0c;可直接运行。 128matlab多元函数极值 (xiaohongshu.com)

Sectigo有几种泛域名SSL证书买一年送一个月

Sectigo是一家知名的数字证书颁发机构&#xff0c;提供了很多种类型的SSL证书&#xff0c;可以满足不同用户的需求。其中&#xff0c;泛域名SSL证书是一种常见的证书类型&#xff0c;可以同时保护主域名以及主域名下所有子域名。今天就随SSL盾小编了解Sectigo旗下有几种泛域名S…

【origin】负载牵引的Smith圆图

【origin】负载牵引的Smith圆图 1.从ADS导入数据到origin2.smith圆图3.扩展到多组线4.参考资料 1.从ADS导入数据到origin export导出为txt&#xff0c;得到的是幅相值&#xff0c;复制到excel如下图&#xff0c;有多根类似格式的线&#xff0c;只需要复制DE列到origin中 复制到…