数据结构自学Day6 栈与队列

1. 栈

        其实栈与队列仍然属于线性表(有n个元素构成的集合,逻辑结构呈现线形)

线形表:顺序表,链表,栈,队列,串(字符串)

栈(Stack)是一种线性数据结构,进行数据插入和删除的一段成为栈顶,另外一段称为栈底,数据元素遵守“后进先出” (LIFO, Last In First Out)

栈的插入数据 --压栈/进栈,入数据在栈顶

栈的删除数据 -- 出栈,出数据也在栈顶。

这里栈如何实现呢?考虑(LIFO: 后进先出)

如果是双向链表的话,无所谓栈顶与栈底的位置。

2. 栈的实现

        栈的实现利用数组实现提高内存访问效率

1、栈的初始化      

typedef int STDataType;
#define Ini_capacity 5typedef struct Stack
{int* _val;int _size;int _capacity;
}Stack;void StackInit(Stack* pst){assert(pst);// pst->_val = NULL;// pst->_capacity = 0;// pst->_size = 0;pst->_val = (STDataType*) malloc(Ini_capacity*sizeof(STDataType));if(pst->_val == NULL){perror("malloc");exit(-1);}pst->_size = 0;pst->_capacity =Ini_capacity;}

2、压栈(入栈操作)

// 入栈
void StackPush(Stack* pst,STDataType Val){assert(pst);if(pst->_size == pst->_capacity){//增容pst->_capacity = 2*pst->_capacity;STDataType* tmp = realloc(pst->_val,pst->_capacity*sizeof(STDataType));pst->_val = tmp;tmp = NULL;}pst->_val[pst->_size] = Val;pst->_size++; 
}

3、出栈操作

void StackPop(Stack* pst){assert(pst && pst->_size > 0);--pst->_size;
}

4 、返回栈内数据个数,是否为空,以及栈顶元素

//获取数据个数
int StackSize(Stack* pst){assert(pst);return(pst->_size);
}
//返回1 是空,返回0是非空
int StackEmpty(Stack* pst){assert(pst);// return pst->_size == 0 ? 1 : 0;return !pst->_size;
}
//获取栈顶数据 
STDataType StackTop(Stack* pst){assert(pst && pst->_size>0);return pst->_val[pst->_size-1];
}

5、栈的摧毁,释放空间

//栈的摧毁
void StackDestroy(Stack* pst){assert(pst);free(pst->_val);pst->_val = NULL;pst->_size =pst->_capacity = 0;
}

3、栈的常见应用:

  • 1、函数调用(函数栈帧)

  • 2、括号匹配(如表达式合法性)

  • 3、 浏览器历史记录(后退/前进)

  • 4、深度优先搜索(DFS)迷宫问题

4、队列

        队列(Queue)是一种线性数据结构:一个典型的队列有两个端:Front(队首):元素被取出的地方 Rear(队尾):元素被加入的地方。它的特点是:先进先出(FIFO, First In First Out)。

同样,队列的实现也可以通过数组和链表进行实现。?考虑(FIFO: 后进先出)。

数列出队列有些麻烦:需要挪动数据,因为队头的数据出队列后,队尾数据需要补充。

单链表入队列只需要尾插,出队列只需要将头节点给到下一个节点,然后free即可。

5、队列的实现

       队列的实现利用单向链表

1、队列的初始化 (保存队列的头指针,尾指针)

//利用单向链表的形式实现栈
typedef int QeDataType;typedef struct QueueNode
{QeDataType _data;struct QueueNode* next;
}QueueNode;
//存储队列的头,尾指针用于插入和删除队列元素
typedef struct Queue
{QueueNode* _head;QueueNode* _tail;
}Queue;//队列的初始化
void QueueInit(Queue* pq){assert(pq);pq->_head = pq->_tail = NULL;
}

2、队列新增元素

//队列插入元素
void QueuePush(Queue* pq, QeDataType x){assert(pq);QueueNode*NewNode = (QueueNode*)malloc(sizeof(QueueNode));if(NewNode == NULL){perror("malloc");exit(-1);}NewNode->next=NULL;NewNode->_data = x;if(pq->_head == NULL){pq->_head = pq->_tail = (QueueNode*)malloc(sizeof(QueueNode));}else{pq->_tail->next = NewNode;pq->_tail = NewNode;}
}

3、队列删除元素

//队列删除元素
void QueuePop(Queue* pq){assert(pq);if(pq->_head == NULL){printf("队列为空\n");exit(-1);}QueueNode* head_next = pq->_head->next;free(pq->_head);pq->_head = head_next;if(pq->_head == NULL){pq->_tail = NULL;}
}

4、取出队列头数据和尾数据

//取出队头数据
QeDataType QueueFront(Queue* pq){assert(pq);if(pq->_head ==NULL){return NULL;}return pq->_head->_data;
}
//取出队尾数据
QeDataType QueueBack(Queue* pq){assert(pq);if(pq->_tail ==NULL){return NULL;}return pq->_tail->_data;
}

5、检查队列是否为空,返回队列大小

//检查队列是否为空,返回队列大小
int QueueEmpty(Queue* pq){assert(pq);return !pq->_head;
}
int QueueSize(Queue* pq){assert(pq);if(pq == NULL){return 0;}QueueNode* Cur = pq->_head;int count =0;while(Cur || Cur != pq->_tail) {count++;Cur = Cur->next;}return count;
}

6、队列的常见应用

应用场景

描述

操作系统调度

CPU 任务调度用就绪队列

消息队列系统

线程/服务之间的数据传输

广度优先搜索(BFS)

图的遍历

打印任务排队

打印服务器依次处理任务

缓存机制(例如先进先出缓存)

维护历史数据

银行/售票排队系统

模拟现实中等待排队的流程

栈与队列,是程序运行背后的“隐形骨架”,掌握它们,你就掌握了高效处理顺序、回退、排队等核心能力,是走向算法高手的第一步。

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

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

相关文章

Java 异常处理详解:从基础语法到最佳实践,打造健壮的 Java 应用

作为一名 Java 开发工程师,你一定遇到过运行时错误、空指针异常、文件找不到等问题。Java 提供了强大的异常处理机制,帮助我们优雅地捕获和处理这些错误。本文将带你全面掌握:Java 异常体系结构try-catch-finally 的使用throw 与 throws 的区…

Fiddler弱网测试实战指南

Fiddler是一个常用的网络抓包工具,它也可以用来模拟弱网环境进行测试。 在测试时需要用到弱网测试,也就是在信号差、网络慢的情况下进行测试。比如,用户在地铁、电梯、地下车库等场景经常会遇到会话中断、超时等情况,这种就属于弱…

解决Vue页面黑底红字遮罩层报错:Unknown promise rejection reason (webpack-internal)

vue前端页面弹出黑底红色报错遮罩层报错:具体报错信息:Uncaught runtime errors: ERROR Unknown promise rejection reasonat handleError (webpack-internal:///./node_modules/webpack-dev-server/client/overlay.js:299:58)at eval (webpack-internal…

构建 Go 可执行文件镜像 | 探索轻量级 Docker 基础镜像(我应该选择哪个 Docker 镜像?)

文章目录构建 Go 可执行文件镜像典型用途探索轻量级 Docker 基础镜像构建 Go 可执行文件镜像 golang:1.23.0-bullseye 是官方 Go 镜像的一个 “build-stage” 版,用来构建 Go 可执行文件,而不是把它当成最终运行镜像。 dockerhub官方:https://hub.dock…

链表算法之【回文链表】

目录 LeetCode-234题 LeetCode-234题 给定一个单链表的头节点head,判断该链表是否为回文链表,是返回true,否则返回false class Solution {/*** 这里的解题思路为:* (1)、找中间节点* (2)、反转链表* (3)、遍历比较节点值是否相…

Playwright Python 教程:网页自动化

1. 常用工具简介及对比主流网页自动化工具对比工具支持语言浏览器支持特点适用场景PlaywrightPython, JS, .NETChromium, Firefox, WebKit跨浏览器、速度快、API简洁自动化测试、爬虫、网页操作Selenium多语言所有主流浏览器历史悠久、社区大传统自动化测试、兼容性测试Puppete…

动态数组:ArrayList的实现原理

动态数组:ArrayList的实现原理 大家好!今天我们来聊聊Java集合框架中一个非常重要的数据结构——ArrayList。就像我们日常生活中使用的伸缩收纳盒一样,ArrayList可以根据需要自动调整大小,既方便又高效。那么它是如何实现这种&quo…

MIPI DSI(五) DBI 和 DPI 格式

关于 DBI 和 DPI 这两种格式的详细协议内容,请参考《MIPI Alliance Standard for Display Bus Interface(V2.0) .pdf》和《MIPI Alliance Standard for Display Pixel Interface(DPI- 2) .pdf》这两份文档。首先先了解…

FRP Ubuntu 服务端 + MacOS 客户端配置

一、服务端配置 1、下载frp并解压 # 创建目录并进入 mkdir -p /opt/frp && cd /opt/frp # 下载最新版(替换URL为GitHub发布页最新版本) wget https://github.com/fatedier/frp/releases/download/v0.59.0/frp_0.59.0_linux_amd64.tar.gz # 解压 …

Video Python(Pyav)解码二

在 PyAV 中,input_container.decode() 和 input_container.demux() 是两种处理视频流数据的不同方法,它们分别适用于不同的场景。下面通过代码示例和对比来详细说明它们的用法和区别。1. input_container.decode()功能直接解码:从容器中读取数…

闲庭信步使用图像验证平台加速FPGA的开发:第十六课——图像五行缓存的FPGA实现

(本系列只需要modelsim即可完成数字图像的处理,每个工程都搭建了全自动化的仿真环境,只需要双击top_tb.bat文件就可以完成整个的仿真,大大降低了初学者的门槛!!!!如需要该系列的工程…

头文件与源文件及区别

使用场景上的区别头文件:变量的声明,函数的声明,宏的定义,类的定义等。 源文件:变量的定义。函数的定义实现,类成员函数的定义实现等。这样方便于我们去管理、规划,更重要的是避免了重定义的问题…

图机器学习(4)——图机器学习与嵌入算法

图机器学习(4)——图机器学习与嵌入算法0. 前言1. 图机器学习1.1 机器学习基本原理1.2 图机器学习的独特优势2. 广义图嵌入问题3. 图嵌入算法分类小结0. 前言 机器学习是人工智能的一个重要分支,它致力于让系统能够从数据中自主学习并持续优…

网络基础10--ACL与包过滤

一、ACL 定义与核心功能ACL(访问控制列表)是通过规则匹配实现数据包过滤或分类的核心技术,广泛应用于包过滤、NAT、QoS、路由策略等场景。其核心由规则条目组成,每条规则包含匹配条件(如源 / 目 IP、端口、协议&#x…

Web安全 - 基于 SM2/SM4 的前后端国产加解密方案详解

文章目录概述一、背景与法规要求二、算法选型三、核心流程四、前端实现要点(伪代码)五、后端实现要点(伪代码)六、公钥存储策略七、全流程示例图八、总结与最佳实践推荐概述 随着信息安全法规日益严格,如《网络安全法》《数据安全法》和等保…

ACL动态路由实验全攻略:配置与安全实战

实验拓扑图 实验需求 步骤1.按照图示配置IP地址2.按照图示区域划分配置对应的动态路由协议3.在R7上配置dhcp服务器,能够让pc可以获取IP地址4.将所有环回宣告进ospf中,将环回17宣告进rip中,将rip路由引rospf中,ospf路由引.rip中5.要…

电动汽车制动系统及其工作原理

制动系统是实现车辆减速、停车功能的重要系统。电动汽车的制动系统按照制动实现方式分为机械制动和电机再生制动,机械制动根据制动力实现方式不同又可分为液压机械制动系统、气压机械制动系统和电子机械制动系统。目前,电动汽车的制动系统实现一般为协调…

CentOS 7 Linux 离线安装 docker-compose

CentOS 7 Linux 离线安装 docker-compose 1. docker-compose 简介 1.1. docker-compose 是什么? docker-compose 是 Docker 官方提供的工具,用于定义和运行多容器 Docker 应用程序。通过一个 YAML 文件(通常为 docker-compose.yml&#xf…

排序算法实战(上)

一、引言在力扣刷题的旅程中,排序类题目是绕不开的重要板块。今天就来分享两道经典排序题——912. 排序数组和75. 颜色分类的解题思路与代码实现,带你深入理解排序算法在实际题目中的应用 。二、题目剖析与解题思路(一)912. 排序数…

python学智能算法(二十)|SVM基础概念-感知机算法及代码

引言 前序学习进程中,已经学习了超平面的基础知识,学习链接为:超平面 在此基础上,要想正确绘制超平面,还需要了解感知机的相关概念。 感知机 感知机是对生物神经网络的模拟,当输入信号达到感知机的阈值时…