数据结构九——栈

文章出处:极客时间《数据结构和算法之美》-作者:王争。该系列文章是本人的学习笔记。

1栈的定义

1.1 栈的定义

栈:后进者先出,先进着后出。就像一碟盘子,如果拿走一个盘子,拿走的一定是最后放上去的那个。栈是一种操作受限的线性表,只允许在一端插入和删除。本质上来说就是一个操作不方便的数组或者链表。

栈存在的意义是什么?数据结构本身就是对特定场景的抽象,要求操作不多不少,正好满足场景需求。过多的接口会带来操作不可控,进而操作结果不可预计。

1.2 实现栈

我们可以使用数组实现一个栈,称为顺序栈;也可以用链表实现一个栈,称为链式栈。

/*** 数组实现的栈,在一端插入和删除,那就对数组的最后一个元素操作吧*/
public class ArrayStack {//存储数据的值private int[] items;//容量private int n;//存储元素个数private int size;/**** @param capacity*          容量*/public ArrayStack(int capacity){this.n = capacity;items = new int[n];}/*** 添加元素,如果还有空间则添加成功,返回true。否则返回false。* @param val* @return*/public boolean push(int val){if(this.size >=n) return false;items[size++] = val;return true;}/*** 栈内元素个数* @return*/public int size(){return this.size;}/*** 删除栈顶元素。如果当前栈内没有元素,则抛出异常。在调用pop之前先调用size()吧。* @return*/public int pop(){if(size==0) throw new IllegalArgumentException("栈目前没有任何元素,不能弹出元素");return items[--size];}
}

复杂度分析。push,pop时间复杂度为O(1),即使链表实现的栈也一样。空间复杂度式O(n)。需要大小为n的数组存储栈内元素。

1.3 支持动态扩容的栈

上面的实现中,当栈内没有空间的时候,就不能再插入元素。如果实现一个空间不受限的栈呢?这是一个数组自动扩容、自动减少空间的过程。我们只需要判断在数组满了的时候申请一个2倍容量的数组,将原有元素拷贝过去。

当栈内元素只有数组容量1/4的时候,将数组容量缩小到一半。当然对内存空间不敏感的应用可以不用做这一步。

	/*** 添加元素* @param val*/public void push(int val){if(this.size >=n) {grow();}items[size++] = val;}private void grow() {int newSize = 2*size;int[] newItmes = new int[newSize];System.arraycopy(this.items,0,newItmes,0,size);this.n = newItmes.length;this.items = newItmes;}

接下来我们分析一下支持动态扩容的栈入栈时间复杂度是多少。入栈操作的平均时间复杂度用摊还分析法。为了分析方便,我们先做以下假设:
1 只有扩容操作,扩容为原来数组2倍大小;
2 只有push,没有pop操作;
3 定义不涉及内存搬移的入栈操作为simple-push。

如果当前数组大小为K,当再有新的数据入栈的时候,需要申请一个大小为2K的数组,并且有K次数据迁移的操作。但是接下来的K-1次入栈操作,就无需申请内存和迁移数据。

如图所示,第K次入栈,需要的K次迁移操作,可以均摊到到未来K-1次入栈操作。所以这K次操作,平均下来每次是一次数据迁移和一个simple-push。时间复杂度O(1)。

2栈的应用

2.1 栈在函数调用中的应用

2.2 栈在表达式求值中的应用

2.3 栈在括号匹配中的应用

3 浏览器支持前进后退操作

浏览器前进、后退操作是这样的。当你访问页面 a->b->c之后,你可以按后退按钮回到页面b,再继续按前进按钮到页面c。

我们使用两个栈X、Y来完成浏览器的前进后退操作。当访问页面的时候,我们按照顺序将页面入栈X。当按后退按钮的时候,从X栈取出元素,入栈Y。当按前进按钮的时候,从Y栈取出元素,入栈X。当X栈为空的时候,后退按钮不能用。当Y栈为空的时候,前进按钮不能用。

例如初始:
X
Y

访问页面a:
X:a
Y

访问页面b:
X:a,b
Y
访问页面c:
X:a,b,c
Y

按后退按钮,展示页面b:
X:a,b
Y:c

按后退按钮,展示页面a:
X:a
Y:c,b

按前进按钮,从页面a到页面b:
X:a,b
Y:c

这个时候,你访问了新页面d,这时候前进按钮应该不能用,因为d的下一个页面还没有产生;按后退按钮的话应该回到b;所以c页面不能通过前进后退转到,需要清空Y栈:
X:a,b,d
Y:

4 思考

Java虚拟机中有堆栈的概念。栈内用来存储临时变量和方法调用,堆内存储Java对象。那么Java虚拟机中的栈和这里的栈,概念一样吗?
答:不一样。数据结构中的栈是对场景的抽象,是抽象的数据机构。
JVM使用的内存分为代码区、静态数据区和动态数据区。
代码区:存放方法的二进制代码,控制代码区代码执行切换。
静态数据区:全局变量、静态变量,常量(包含final修饰的和String)。
动态数据区:分为堆区和栈区。堆区存放对象,该对象的引用存放在栈区。栈区存放运行方法的形参、局部变量和返回值。

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

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

相关文章

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol Cryptography][第33篇]Bellcore攻击是如何攻击使用CRT的RSA的?

这是一系列博客文章中最新的一篇,该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 转载链接:https://www.cnblogs.com/zhuowangy2k/p/12245604.html

spring学习(14):Autowired的使用场景

CompactDisc类 package soundSystem;import org.springframework.stereotype.Component;Component public class CompactDisc {public CompactDisc() {super();System.out.println("compactdisc无参构造方法");}public void play(){System.out.println("正在播…

数据结构十——队列

文章出处:极客时间《数据结构和算法之美》-作者:王争。该系列文章是本人的学习笔记。 1 队列 队列:可以想象成排队买票,先来的人先买,后到的人站在队尾。先进者先出,这就是队列。 队列的操作&#xff1a…

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol Cryptography][第34篇]描述攻击离散对数问题的baby-step/Giant-step方法

这是一系列博客文章中最新的一篇,该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 Baby-step/Giant-step是Dnaiel Shanks为解决DLP问题开发的算法。DLP问题已经是许多现代密码学的困难性基础。…

spring学习(15):required属性

CompactDisc类 package soundSystem;import org.springframework.stereotype.Component; //注解Componentpublic class CompactDisc {public CompactDisc() {super();System.out.println("compactdisc无参构造方法");}public void play(){System.out.println("…

算法十——深度优先搜索和广度优先搜索

文章出处:极客时间《数据结构和算法之美》-作者:王争。该系列文章是本人的学习笔记。 搜索算法 算法是作用于数据结构之上的。深度优先搜索、广度优先搜索是作用于图这种数据结构之上的。图上的搜索算法可以理解为从一个顶点到另外一个顶点。 常用的搜…

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol 52][第35篇]给针对ECDLP问题的Pollard rho,parallel Pollard rho攻击的一个粗略的描述

这是一系列博客文章中最新的一篇,该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 [1] http://www.cs.bris.ac.uk/~nigel/Crypto_Book/book.ps (pages 208 - 214) 转载连接:https…

spring学习(16):使用接口

目录结构 pom.xml <?xml version"1.0" encoding"UTF-8"?> <project xmlns"http://maven.apache.org/POM/4.0.0"xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation"http://maven.apache.org/P…

交易系统高并发下的幂等性设计原则

一、介绍 幂等性就是针对同一个请求&#xff0c;不管该请求被提交了多少次&#xff0c;该请求都将被视为同一个请求&#xff0c;服务端不应该将同一个请求进行多次处理&#xff0c;以确认处理逻辑的正确性&#xff0c;针对交易性系统幂等性的设计尤为重要&#xff0c;否则由于网…

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol Cryptography][第36篇]Index Calculus算法

这是一系列博客文章中最新的一篇&#xff0c;该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 我们这篇博客继续描述一种数学攻击&#xff0c;这种数学攻击被叫做Index Calculus(IC)算法。 注意这里Index…

DS博客作业07--查找

1.本周学习总结 1.思维导图 2.谈谈你对树结构的认识及学习体会。 查找是一种跟我们生活息息相关的算法&#xff0c;最典型的例子就是搜索引擎&#xff0c;而评价一种查找算法的优劣的关键就是查找速度&#xff0c;生活中我们往往要在大量数据查找自己所需要的东西&#xff0c;如…

easyUI学习笔记二

1&#xff0e; 拖拉大小 <!DOCTYPE html> <html> <head><title>easyui学习</title><script type"text/javascript" src jquery-easyui/jquery.min.js> </script><script type"text/javascript" src jquer…

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol Cryptography][第37篇]The Number Field Sieve

这是一系列博客文章中最新的一篇&#xff0c;该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 转载链接&#xff1a;https://www.cnblogs.com/zhuowangy2k/p/12245636.html

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol52]40一般来说SPA和DPA的区别是什么

这是一系列博客文章中最新的一篇&#xff0c;该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 电磁(Electronmagnetic, EM)功率分析攻击被划分成两种类型的攻击&#xff0c;简单功率分析(SPA)或者差分功率…

LDAP入门

LDAP入门 首先要先理解什么是LDAP&#xff0c;当时我看了很多解释&#xff0c;也是云里雾里&#xff0c;弄不清楚。在这里给大家稍微捋一捋。首先LDAP是一种通讯协议&#xff0c;LDAP支持TCP/IP。协议就是标准&#xff0c;并且是抽象的。在这套标准下&#xff0c;AD&#xff08…

spring学习(22):分层架构

pom.xml <?xml version"1.0" encoding"UTF-8"?> <project xmlns"http://maven.apache.org/POM/4.0.0"xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation"http://maven.apache.org/POM/4.0.0 …

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol52]42蒙哥马利乘法,哪里泄漏侧信道路吗?

这是一系列博客文章中最新的一篇&#xff0c;该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 看看你的C代码为蒙哥马利乘法&#xff0c;你能确定它可能在哪里泄漏侧信道路吗? 几个月前(回到3月份)&…

深度学习02——Softmax、DNN、WideDeep Model

说明&#xff1a;本系列是七月算法深度学习课程的学习笔记 1 背景介绍 深度学习在图片上的应用&#xff1a;功能上讲&#xff1a;图像分类和物体识别&#xff1b;应用上&#xff1a;可以用来分类图片&#xff1a;白菜形状的玉器摆件、白菜、大白菜&#xff1b;图片搜索&#…

[密码学基础][每个信息安全博士生应该知道的52件事][Bristol52]44在ECC密码学方案中基本的防御方法

这是一系列博客文章中最新的一篇&#xff0c;该文章列举了“每个博士生在做密码学时应该知道的52件事”:一系列问题的汇编是为了让博士生们在第一年结束时知道些什么。 在ECC密码学方案中&#xff0c;描述一些基本的防御方法 在上篇文章中我们提到了在ECC中对抗侧信道攻击的一…

第六十五期:央行万字工作论文:区块链能做什么、不能做什么?

本文从经济学角度研究了区块链的功能。首先&#xff0c;在给出区块链技术的经济学解释的基础上&#xff0c;归纳出目前主流区块链系统采取的“Token 范式”&#xff0c;厘清与区块链有关的共识和信任这两个基础概念&#xff0c;并梳理智能合约的功能。 作者&#xff1a;徐忠 邹…