本节内容

1.栈和队列的特性

栈:后进先出

•栈:受限制的线性表,只允许从表的一端操作。这端称为栈顶,另一端为栈底

•压入元素(push):往栈顶新增一个元素,新元素成为新栈顶。

•弹出元素(pop):移除栈顶元素,原栈顶的元素成为新栈顶/或栈变成空栈

•图片表示进出栈结果:

 *key1:栈是一种先进后出的数据结构,pop和push操作仅在栈顶进行

队列:先进先出

•队列:受限制的线性表,只允许从表的两端操作,一端是队首,一端是队尾。

•入队(enqueue):往队尾新增一个元素,新元素成为新队尾

•出队(dequeue):移出队首元素,下一个元素成为新队首/或队列变为空

•图文演示过程:

2.栈和递归

•栈后进先出的特点天然地和程序中函数调用关系相吻合

•程序执行时,在函数A中执行到调用另一个函数B的语句时,会发生什么?

立刻进入被调函数B执行其代码,完成后返回到A的下一行继续执行A的剩余代码

•因此在操作系统执行代码时,函数间的调用-返回关系正是通过调用栈来维护

•函数的递归调用本质也是一个栈型调用,因此可以利用栈将一个递归函数改写为完全等价的非递归函数,避免了操作系统层面的调用栈开销。

3.栈和队列的应用

栈的应用:括号匹配

•目的:判断一个字符串你中括号是否——匹配

•为什么可以用栈来解决这个问题?

•当遇到左括号时,我希望能立刻遇到它的另一半,但如果接着又遇到了一个左括号,那它的需求比我更紧迫,我需要先处理后来的这个左括号

•后来的需要先满足->后进先出问题->用栈解决

栈的应用

•表达式求值,如1+2*3

•进制转换

•非递归的深度优先遍历(DFS)

队列的应用:循环队列(循环队列基于顺序序列)

•你会怎样实现一个顺序序列?

•'假溢出'现象:底层顺序表前部的可用空间无法再利用上了

•解决方法:循环队列

4.代码实现

顺序栈实现

•顺序栈的底层是一个数组,低地址为栈底,高地址为栈顶,只能在栈顶操作

/*(顺序)栈*/
//栈数据结构定义
#define MAX_SIZE 10
typedef struct{Student *data;int size;
}Stack;
//往栈顶压入一个元素
bool Push(Stack &stk,const Student &s){if (stk.size==MAX_SIZE){return false;
}
int newTop=stk.size;
stk.data[newTop]=s;
stk.size++;
return true;
}
//弹出栈顶元素
bool Pop(Stack &stk){if(stk.size==0){return false;}
stk.size--;
return true;
}

*key1:顺序栈的底层是一个数组空间,并通过维护当前栈大小实现栈

*key2:顺序栈的当前栈顶元素下标和栈大小是top=size-1的关系

1.设Stack是顺序栈的一种实现,在(a)处应填入的代码为:___________.(stk.size--)

struct Stack{

Elem data[MAX_SIZE];

int size=0;

};

bool Pop(Stack &s){

if (stk.size==0)return false;

___(a)____;

return true;

}

循环队列实现

•循环队列的底层是一个数组,通过维护队头和队尾在此数组中的下标来实现

/*循环队列*/
//循环队列数据结构
#define M 10
typedef struct{Student data[M];int front;int back;//bcak表示队尾的下一个空位
}CQueue;//c=Circulative
//求循环队列元素个数
int GetSize(CQueue &queue){int size=(queue.back-queue.front+M)%M;return size;
}

*key1:循环队列的容量是MAX_SIZE-1

*key2:循环队列当前元素数量计算

1.假设一循环队列的底层数组为array[M],我们约定f表示为当前队首元素,b为当前队尾元素的后

一个元素,则当前队列内元素个数为()

A.b-f                B.(b-f+M)%M

C.b-f+M           D.(f-b+M)%M

分析:做循环队列题一定要把底层数组画出来模拟!

第一种情况:

第二种情况:

M=8,蓝色表示队列元素。

分析:对于第一种情况直接=b-f,第二种情况等于b-f+M

统一一下答案:由于b-f>0,所以加上M再对M取余正好消去M。第二个由于b-f<0,b-f+M<M

所以对M取余不起作用。总结答案选择为B选项

循环队列实现

•循环队列的底层是一个数组,通过维护队头和队尾在此数组中的下标来实现

//循环队列入列
bool Enqueue_CQ(CQueue &queue,const Student &s){int newBack=(queue.back+1)%M;if(newBack==queue.front){return false;//头尾相接表示队列满了}queue.data[queue.back]=s;//放入队尾queue.back=newBack;return true;
}
//循环队列出列
bool Dequeue_CQ(CQueue &queue){if (queue.front==queue.back){return false;//头尾重合表示队列为空
}   queue.front=(queue.front+1)%M;return true;}

*key3:循环队列判满条件为(back+1)%MAX_SIZE==front ''首尾相接''

*key4:循环队列判空条件为back==front                                     ''首尾重合''

1.(a)处应填入的代码为:______________.(queue.front ==queue.back)

bool Dequeue_CQ(CQueue &queue){

if (___(a)____){

return false;//头尾重合表示队列为空

}queue.front=(queue.front +1)%queue.capacity;

return true;

}

练习:

完整代码:

/*
Ch3 栈和队列
*/
// 实例数据元素:学生
typedef struct {char id[10];int age;double score;
} Student;
/* (顺序)栈 */
// 栈数据结构定义
#define MAX_SIZE 10
typedef struct {Student *data;int size;
} Stack;
// 初始化栈
Stack Create() {Stack stk;stk.data = new Student[MAX_SIZE];stk.size = 0;return stk;
}
// 获取栈顶元素
bool Top(Stack &stk, Student &res) {if (stk.size == 0) {return false;}int top = stk.size - 1;res = stk.data[top];return true;
}
// 弹出栈顶元素
bool Pop(Stack &stk) {if (stk.size == 0) {return false;}stk.size--;return true;
}
// 往栈顶压入一个元素
bool Push(Stack &stk, const Student &s) {if (stk.size == MAX_SIZE) {return false;}int newTop = stk.size;stk.data[newTop] = s;stk.size++;return true;
}
/* 栈的应用:括号匹配 */
#include <stack>
#include <string>
bool IsParenthesesMatch(std::string s) {std::stack<char> stk;for (int i = 0; i < s.length(); ++i) {switch (s[i]) {case '(':case '[':case '{':stk.push(s[i]);break;case ')':if (stk.empty() || stk.top() != '(') {return false;}stk.pop();break;case ']':if (stk.empty() || stk.top() != '[') {return false;}stk.pop();break;case '}':if (stk.empty() || stk.top() != '}') {return false;}stk.pop();break;}}return stk.empty();
}
/* 循环队列 */
// 循环队列数据结构
#define M 10
typedef struct {Student data[M];int front;int back;  // back表示队尾的下一个空位
} CQueue;      // C = Circulative
// 循环队列入队
bool Enqueue_CQ(CQueue &queue, const Student &s) {int newBack = (queue.back + 1) % M;if (newBack == queue.front) {return false;  // 头尾相接表示队列满了}queue.data[queue.back] = s;  // 放入队尾queue.back = newBack;        // 移动backreturn true;
}
// 循环队列出队
bool Dequeue_CQ(CQueue &queue) {if (queue.front == queue.back) {return false;  // 头尾重合表示队列为空}queue.front = (queue.front + 1) % M;return true;
}
// 求循环队列元素个数
int GetSize(CQueue &queue) {int size = (queue.back - queue.front + M) % M;return size;
}

栈和队列的操作和应用相关推荐

  1. 面试题(用栈代替队列的操作和原生map实现)

    是skype电话面试,先行记录下来,总共有两道: 1. 通过栈的操作实现队列的操作: 即 用栈的基本方法push  pop 实现 出队和入队的方法 难点在于在不给出提示的情况下,能不能想出使用两个栈来 ...

  2. LinkedList 模拟栈和队列

    LinkedList 比ArrayList 提供了更多的方法,其中有两个方法可以实现栈和队列的操作. removeFirst() 移除并返回此列表中的第一个元素. removeLast() 移除并返回 ...

  3. Java停车场管理系统使用栈和队列任务台程序

    运行截图: (栈和队列) 点此去下载 在学习过程中,总结到的规律: 栈功能(仅有增删,无查改) • 入栈–增 • 出栈–删 队列功能(仅有增删,无查改) • 入队–增 • 出队–删 二者由于自身特性限 ...

  4. 剑指Offer的学习笔记(C#篇)-- 用两个栈实现队列

    题目描述 用两个栈来实现一个队列,完成队列的Push和Pop操作. 队列中的元素为int类型. 一 . 概念! 首先要理解栈和队列的概念. 1. 栈:咱可以简单的把栈理解成装羽毛球的球桶.或者我们吃的 ...

  5. 数据结构实验报告—栈和队列

    作者:命运之光 专栏:数据结构 目录 实验内容 实验三 栈和队列 一.需求分析 二.概要设计 三.详细设计 四.调试分析 五.测试结果 附录:源程序代码(带注释) 实验内容 实验三栈和队列 实验环境: ...

  6. 用两个栈做队列(左程云算法学习)

    利用两个栈实现队列的操作 ` 题目:编写一个类,用两个栈实现队列,支持队列的基本操作(add,poll,peek) 解答:栈:先进后出 队列:先进先出 设置两个栈,分别为stackPush 和stac ...

  7. ADT栈与队列的C语言编程与实现

    一 .目的: 加深对抽象数据类型 ADT 栈和队列的理解: 二 .环境: operating system version:Win11 CPU instruction set:  x64 Integr ...

  8. 数据结构(一)——链表与邻接表、栈与队列、KMP

    前言 重学算法第3天,希望能坚持打卡不间断,从基础课开始直到学完提高课. 预计时长三个月内,明天再来!肝就完了 2月15日,day03 打卡 今日已学完y总的 算法基础课-2.1-第二章 数据结构(一 ...

  9. 10.数据结构:栈和队列

    大家好,我王有志又回来啦.关注王有志,回复DSA获取数据结构和算法学习资源. 最近被全链路优化搞得焦头烂额,等抽出时间来和大家分享下我司正在做的"全面提速工程". 今天我们来学习线 ...

最新文章

  1. 5如何将表格的一行数据清空_微信公众号推文中如何自定义添加表格?
  2. js 前端操作的分页路由设计
  3. Linux 基础知识(十)DNS服务器主从复制,子域授权
  4. oracle对象权限 函数,oracle的系统和对象权限
  5. python分片上传_python 分片上传大格式
  6. 标题在优化排名的写法
  7. C# MessageBox 使用总结
  8. android root大师,安卓Root成难题?ROOT大师帮你一键Root
  9. 网络工程师职场进化手册
  10. 医院排队系统排队叫号系统
  11. 在AIX环境下实施Oracle 集群RAC的结构 文平
  12. 电脑画流程图用什么软件好?这3款软件很好用
  13. matlab图形设计界面 文献翻译,毕业设计基于matlab的数字图像识别的设计与实现文献翻译V8.1(资料4)...
  14. 大学物理复习笔记——相对论
  15. 全数字OQPSK调制解调的基本算法,包括成形滤波器、NCO模型、载波恢复
  16. CentOS 7之ifconfig
  17. 如何让你的App永远在后台存活:对Android进程守护、闹钟后台被杀死的研究
  18. 来自西弗吉利亚大学li xin整理的CV代码合集(转)
  19. 戴尔服务器型号t300,常见的服务器种类戴尔服务器的类别有哪些?戴尔服务器产品大盘点...
  20. 一个网站访问速度测试工具

热门文章

  1. 六堡一箩筐首场线下品鉴会+线上直播助推六堡茶营销创新
  2. textarea赋值有很多空格和空行
  3. 基础的01字串 蓝桥杯基础题
  4. scapy定制数据包详解
  5. listagg用mysql实现_Oracle 11g 列转行listagg
  6. #gcc笔记01#gcc编译选项 -O0 -O1 -O2 -O3
  7. java GUI版坦克大战
  8. MySQL问题记录(Linux)
  9. 调用android自带分享功能,分享图片文字等信息。
  10. Mr. Holmes(福尔摩斯先生观后感)--尖锐直白了一生,却以谎言结尾。