版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、第5章 堆栈,-后进先出:一种操作受限的线性表,a,2,主要内容,堆栈的定义 堆栈的描述 公式化描述 链表描述 堆栈的应用 括号匹配、汉诺塔、火车车厢重排 迷宫、开关盒布线、离线等价类,a,3,堆栈定义,栈顶,栈底,堆栈(stack)是一个线性表,其插入和删除操作都在表的同一端进行,这端被称为栈顶(top),另一端被称为栈底(bottom) LIFO Last in, First out,a,4,a,5,a,6,抽象数据类型,抽象数据类型Stack 实例 元素线性表,栈底,栈顶 操作 Create():创建一个空的堆栈 IsEmpty():如果堆栈为空,则返回true,否则返回false Is
2、Full():如果堆栈满,则返回true,否则返回false Top():返回栈顶元素 Push(x):向堆栈中添加元素x Pop(x):删除栈顶元素,并将它传递给x ,a,7,主要内容,堆栈的定义 堆栈的描述 公式化描述 链表描述 堆栈的应用 括号匹配、汉诺塔、火车车厢重排 迷宫、开关盒布线、离线等价类,a,8,公式化描述:继承线性表,template class Stack : private LinearList / LIFO objects public: Stack(int MaxStackSize = 10) : LinearList (MaxStackSize) bool IsE
3、mpty() const return LinearList:IsEmpty(); bool IsFull() const return (Length() = GetMaxSize();,线性表尾部作为栈顶,a,9,公式化描述(续),T Top() const if (IsEmpty() throw OutOfBounds(); T x; Find(Length(), x); return x; Stack,取栈顶提取最后一个元素,压栈添加到表尾,出栈提取最后一个元素,a,10,实现方法分析,IsFull需要获取数组大小 方法一将类LinearList的成员MaxSize变为protecte
4、d类型 方法二:LinearList类增加函数protected: int GetMaxSize() const return MaxSize;LinearList类的变化不会影响Stack类,更好!,a,11,实现方法分析,继承方式为什么是private? private继承会把基类的所有成员变为派生类的私有成员 栈虽可看作线性表的特例,但毕竟不是 用户使用Stack类,我们希望他们使用Push、Pop,而不是Insert、Delete 而private继承恰好可使Insert、Delete成为Stack的私有成员,用户无法看到,a,12,Stack的效率,构造函数、析构函数与LinearL
5、ist相同 T:基本类型,(1) T:用户自定义类, (MaxStackSize) 其他函数:(1),a,13,H1.自定义的Stack类,template class Stack public: Stack(int MaxStackSize = 10); Stack() delete stack; bool IsEmpty() const return top = -1; bool IsFull() const return top = MaxTop; T Top() const; Stack,a,14,构造函数,template Stack:Stack(int MaxStackSize)
6、/ Stack constructor. MaxTop = MaxStackSize - 1; stack = new TMaxStackSize; top = -1; ,空栈,a,15,Top函数,template T Stack:Top() const / Return top element. if (IsEmpty() throw OutOfBounds(); return stacktop; ,a,16,Push函数,template Stack ,a,17,Pop函数,template Stack ,a,18,数组描述缺陷,与线性表数组描述类似,空间利用率低 两个堆栈特例,空间利用
7、率较高 Push最坏情况(数组满)仍为(ArraySize) Pop (1),a,19,主要内容,堆栈的定义 堆栈的描述 公式化描述 链表描述 堆栈的应用 括号匹配、汉诺塔、火车车厢重排 迷宫、开关盒布线、离线等价类,a,20,链表描述,栈顶在链表哪一端? 尾节点 Push(x)Insert(n, x): (n) Pop(x)Delete(n, x): (n) 首节点 Push(x)Insert(0, x): (1) Pop(x)Delete(1, x): (1),a,21,LinkedStack类,template class LinkedStack : private Chain publ
8、ic: bool IsEmpty() const return Chain:IsEmpty(); bool IsFull() const; T Top() const if (IsEmpty() throw OutOfBounds(); T x; Find(1, x); return x;,a,22,LinkedStack类,LinkedStack,a,23,IsFull函数,template bool LinkedStack:IsFull() const /Is stack full? try ChainNode *p = new ChainNode; delete p; return fa
9、lse; catch (NoMem) return true; 笨拙!,a,24,H2.自定义的链表实现,template class Node friend LinkedStack; private: T data; Node *link; ;,a,25,自定义的链表实现(续),template class LinkedStack public: LinkedStack() top = 0; LinkedStack(); bool IsEmpty() const return top = 0; bool IsFull() const; T Top() const; LinkedStack,a
10、,26,析构函数,template LinkedStack:LinkedStack() / Stack destructor. Node *next; while (top) next = top-link; delete top; top = next; ,a,27,IsFull函数,template bool LinkedStack:IsFull() const / Is the stack full? try Node *p = new Node; delete p; return false; catch (NoMem) return true; ,a,28,Top函数,templat
11、e T LinkedStack:Top() const / Return top element. if (IsEmpty() throw OutOfBounds(); return top-data; ,a,29,Push,template LinkedStack ,a,30,Pop,template LinkedStack ,a,31,H1-2小结,堆栈的两种实现方式,a,32,主要内容,堆栈的定义 堆栈的描述 公式化描述 链表描述 堆栈的应用 括号匹配、汉诺塔、火车车厢重排 迷宫、开关盒布线、离线等价类,a,33,括号匹配,(a*(b+c)+d)+(e-b)符合语法 (a+b)(不符合语
12、法 寻找匹配括号对正确处理和未匹配括号错误报告 括号匹配是一个基础问题,可以引申到 C+编译器 数学公式自动求解,a,34,a,35,a,36,算法设计思路,( a * ( b + c ) + d ) + (e - b),匹配括号的规律? 右括号与谁匹配(如果有的话)? 由左至右处理符号的话,“右”“后”,靠后的先匹配LIFO 用一个栈保存未匹配的左括号 由左至右扫描表达式串,遇左括号,push 遇右括号,与栈顶左括号匹配,pop,嵌套或者并列,最近(右)未匹配左括号,a,37,匹配失败的情况,( a + b ) ) (失败情况的规律 两种情况对应栈中情况,右括号之前无与之匹配的左括号 左括号
13、之后无与之匹配的右括号,遇到一个右括号时,无未匹配的左括号栈空 右括号都处理完时,还有未匹配的左括号表达式串处理完时,栈不空,a,38,括号匹配程序,#include #include #include #include stack.h const int MaxLength = 100; / max expression length,a,39,括号匹配程序(续),void PrintMatchedPairs(char *expr) / Parenthesis matching. Stack s(MaxLength); int j, length = strlen(expr); / scan
14、 expression expr for ( and ) for (int i = 1; i = length; i+) if (expri - 1 = () s.Push(i);,a,40,括号匹配程序(续),else if (expri - 1 = ) try s.Pop(j); / unstack match cout j i endl; catch (OutOfBounds) cout No match for right parenthesis” at i endl; ,a,41,括号匹配程序(续),/ remaining ( in stack are unmatched while
15、 (!s.IsEmpty() s.Pop(j); cout No match for left parenthesis at j endl; ,a,42,括号匹配程序(续),void main(void) char exprMaxLength; cout Type an expression of length at most MaxLength endl; cin.getline(expr, MaxLength); cout The pairs of matching parentheses in” endl; puts(expr); cout are endl; PrintMatchedP
16、airs(expr); ,a,43,运行实例,Type an expression of length at most 100 (d+(a+b)*c*(d+e)-f)() The pairs of matching parentheses in (d+(a+b)*c*(d+e)-f)() are 4 8 12 16 1 19 No match for right parenthesis at 20 22 23 No match for left parenthesis at 21,a,44,汉诺塔,5800+亿年,a,45,问题抽象,3个塔,n个碟子 初始:所有碟子放在1号塔,大的在底下,小的
17、在上面 任务:把碟子移动到2号塔,顺序不变, 可用3号塔辅助 限制 每次只能移动一个碟子 总是大碟子在下,小的在上,a,46,递归解法,移动碟子的方法:move(n, t1, t2, t3)将n个碟子从t1移到t2,t3辅助 可分解为3个步骤 将n-1个碟子从t1移到t3:move(n-1, t1, t3, t2) 将最大的碟子从t1移到t2 将n-1个碟子从t3移到t2:move(n-1, t3, t2, t1),递归规则,基本情况,a,47,汉诺塔递归程序,void TowersOfHanoi(int n, int x, int y, int z) / Move the top n dis
18、ks from tower x to tower y. / Use tower z for intermediate storage. if (n 0) TowersOfHanoi(n-1, x, z, y); cout Move top disk from tower x to top of tower y endl; TowersOfHanoi(n-1, z, y, x); moves(n)=2n-1最少次数,(2n),a,48,汉诺塔的栈实现,#include #include stack.h“ class Hanoi friend void TowersOfHanoi(int); pu
19、blic: void TowersOfHanoi(int n, int x, int y, int z); private: Stack *S4; / array of pointers to stacks ;,a,49,汉诺塔的栈实现,void Hanoi:TowersOfHanoi(int n, int x, int y, int z) int d; / disk number if (n 0) TowersOfHanoi(n-1, x, z, y); Sx-Pop(d); / remove a disk from x Sy-Push(d); / put this disk on towe
20、r y cout Move disk d from tower x to tower y endl; TowersOfHanoi(n-1, z, y, x); ,a,50,汉诺塔栈实现,void TowersOfHanoi(int n) / Preprocessor for Hanoi:TowersOfHanoi. Hanoi X; X.S1 = new Stack (n); X.S2 = new Stack (n); X.S3 = new Stack (n); for (int d = n; d 0; d-) / initialize X.S1-Pop(d); / add disk d to
21、 tower 1 X.TowersOfHanoi(n, 1, 2, 3); ,a,51,汉诺塔栈实现,void main(void) cout Moves for a three disk problem are endl; TowersOfHanoi(3); ,a,52,火车车厢重排问题,货运列车,n节车厢,编号1n 经过车站n车站1,每站卸掉同号车厢 在始发站重新排列车厢,使得车厢按编号排列每站卸掉最后一节车厢即可 转轨站一个入轨、一个出轨、k个缓冲铁轨完成重排 允许三种操作 入轨缓冲轨 缓冲轨出轨 入轨出轨,a,53,图示,列车行进方向,a,54,我们试着自己总结出算法,初始:58174
22、2963,H1,H2,H3,a,55,继续,入:581742出:,H1,H2,H3,3,6,9,a,56,继续,入:581出:,H1,H2,H3,3,6,9,2,4,7,a,57,继续,入:5出:,H1,H2,H3,6,9,7,1 2 3 4,8,a,58,重排算法,缓冲轨后进先出,用堆栈保存车厢号 考虑在出轨顺序,必须栈底大,栈顶小 依次检查入轨车厢编号 如果出轨所需要的下一车厢,缓冲轨 依次检查缓冲轨,若新来的栈顶,入栈 如果=出轨所需要的下一车厢,出轨 缓冲轨中车厢可能满足出轨需要,检查缓冲轨栈顶车厢,如有可能,出栈,出轨,不是一次,要反复做,直至栈中无满足出轨需要的车厢,a,59,重排
23、程序,bool Railroad(int p, int n, int k) / k track rearrangement of car order p1:n. / Return true if successful, false if impossible. / Throw NoMem exception if inadequate space. / create stacks for holding tracks LinkedStack *H; H = new LinkedStack k + 1; int NowOut = 1; / next car to output int minH
24、= n+1; / smallest car in a track int minS; / track with car minH,k=?,为什么不是Stack?,a,60,重排程序(续),/ rearrange cars for (int i = 1; i = n; i+) if (pi = NowOut) / send straight out cout “Move car ” pi “ from input to output”; cout endl; NowOut+; while (minH = NowOut) Output(minH, minS, H, k, n); NowOut+;
25、,a,61,重排程序(续),else / put car pi in a holding track if (!Hold(pi, minH, minS, H, k, n) return false; return true; ,a,62,Output:缓冲铁轨出轨,void Output(int,a,63,Output:缓冲铁轨出轨,/ find new minH and minS / by checking top of all stacks minH = n + 2; for (int i = 1; i = k; i+) if (!Hi.IsEmpty() ,a,64,Hold:入轨缓冲铁轨,bool Hold(int c, int / a car index,a,65,Hold:入轨缓冲铁轨(续),for (int i = 1; i = k; i+) if (!Hi.IsEmpty() / track i not empty x = Hi.Top(); if (c x /
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 医生医疗外科KPI考核表
- 客户对产品的新反馈收集函(5篇)
- 个人家庭漏水事故排除预案
- 信息安全防护数据安全个人及家庭安全预案
- 移动游戏设计师团队创作绩效衡量表
- 艺术之光:发现美与创意思考小学主题班会课件
- 客户关系管理部门互动率考核表
- 行政后勤管理工作绩效评定表
- 培养习惯自律自强小学主题班会课件
- 海康威视:海康观澜大模型白皮书(2026版)
- 2026北京市大兴区瀛海镇人民政府面向社会公开招聘劳务派遣2人笔试参考试题及答案详解
- 优化门诊护理流程提升患者满意度
- 压力容器制造质量管理体系2025年内审资料
- 治本攻坚三年行动台账(模板)
- 神经源性直肠的护理策略
- 临床医学课程思政案例
- 短期与长期应对策略
- JT∕T 850-2013 挤压锚固钢绞线拉索
- 2024届福建省漳州市台商投资区六年级下学期小升初真题数学试卷含解析
- 2024福建检察机关书记员招聘笔试参考题库含答案解析
- 新规公路桥台抗震计算程序
评论
0/150
提交评论