1.引子
1.1.为什么要学习数据结构与算法?
有人说,数据结构与算法,计算机网络,与操作系统都一样,脱离日常开发,除了面试这辈子可能都用不到呀!
有人说,我是做业务开发的,只要熟练API,熟练框架,熟练各种中间件,写的代码不也能“飞”起来吗?
于是问题来了:为什么还要学习数据结构与算法呢?
#理由一:
面试的时候,千万不要被数据结构与算法拖了后腿
#理由二:
你真的愿意做一辈子CRUD Boy吗
#理由三:
不想写出开源框架,中间件的工程师,不是好厨子
1.2.如何系统化学习数据结构与算法?
我想好了,还是需要学习数据结构与算法。但是我有两个困惑:
1.如何着手学习呢?
2.有哪些内容要学习呢?
学习方法推荐:
#学习方法
1.从基础开始,系统化学习
2.多动手,每一种数据结构与算法,都自己用代码实现出来
3.思路更重要:理解实现思想,不要背代码
4.与日常开发结合,对应应用场景
学习内容推荐:
数据结构与算法内容比较多,我们本着实用原则,学习经典的、常用的数据结构、与常用算法
#学习内容:
1.数据结构的定义
2.算法的定义
3.复杂度分析
4.常用数据结构
数组、链表、栈、队列
散列表、二叉树、堆
跳表、图
5.常用算法
递归、排序、二分查找
搜索、哈希、贪心、分治
动态规划、字符串匹配
2.考考你
你还记得在数组那一篇中,我们说过基于线性表的数据结构有哪些吗?它们是:数组、链表、栈、队列。
前面我们详细了解了数组和链表,数组和链表是很多数据结构和算法的基础数据结构。比如我们今天要学习的栈,就可以通过数组实现:顺序栈;也可以通过链表实现:链式栈。
那么问题来了:栈到底是什么样的数据结构呢?
#考考你:
1.你能用自己的话描述栈吗?
2.你知道栈都有哪些常见的应用场景吗?
3.案例
3.1.栈的定义
栈是一种基于线性表的特殊数据结构,说它特殊,是因为栈是操作受限的。栈只允许在栈顶一端插入数据和删除数据。满足后进先出的特点。

3.2.代码实现
顺序栈代码:
package com.anan.struct.linetable;
/**
* 顺序栈:基于数组实现
* @param <E>
*/
public class ArrayStack<E> {
private Object[] items;
private int count;// 计数器(统计栈内元素个数)
private int n;// 栈大小
public ArrayStack(int capacity){
this.items = new Object[capacity];
this.count = 0;
this.n = capacity;
}
/**
* 入栈操作
*/
public boolean push(E e ){
// 检查栈是否满
if(count == n){
return false;
}
// 将元素放入栈中
items[count ++] = e;
return true;
}
/**
* 出栈操作
*/
public E pop(){
// 判断栈是否空
if(count == 0){
return null;
}
// 返回下标为count-1的元素,并且下标-1
E e = (E)items[count - 1];
count --;
return e;
}
public int getCount() {
return count;
}
public int getN() {
return n;
}
}
测试代码:
package com.anan.struct.linetable;
/**
* 测试栈
*/
public class ArrayStackTest {
public static void main(String[] args) {
// 创建栈对象
ArrayStack<Integer> stack = new ArrayStack<Integer>(10);
// 入栈操作
System.out.println("1.入栈操作-----------------------------");
for (int i = 0; i < 5; i++) {
stack.push(i);
System.out.println("当前入栈元素:" + i);
}
System.out.println("出栈前栈中元素个数:" + stack.getCount());
System.out.println("2.出栈操作-----------------------------");
// 出栈操作
for (int i = 0; i < 5; i++) {
System.out.println("当前出栈元素:" + stack.pop());
}
System.out.println("出栈后栈中元素个数:" + stack.getCount());
}
}
测试结果:
D:\02teach\01soft\jdk8\bin\java com.anan.struct.linetable.ArrayStackTest
1.入栈操作-----------------------------
当前入栈元素:0
当前入栈元素:1
当前入栈元素:2
当前入栈元素:3
当前入栈元素:4
出栈前栈中元素个数:5
2.出栈操作-----------------------------
当前出栈元素:4
当前出栈元素:3
当前出栈元素:2
当前出栈元素:1
当前出栈元素:0
出栈后栈中元素个数:0
Process finished with exit code 0
4.讨论分享
#考考你答案:
1.你能用自己的话描述栈吗?
1.1.栈是基于线性表的数据结构
1.2.栈一种操作受限的数据结构
1.3.栈满足后进先出的特点
1.4.栈只允许在栈顶插入元素、和删除元素
2.你知道栈都有哪些常见的应用场景吗?
2.1.方法调用
a.在jvm内存结构中,有线程共享的:方法区、堆
b.在jvm内存结构中,有线程私有的:程序计数器、本地方法栈、虚拟机栈
c.在虚拟机栈中,每个方法调用都被封装成:栈帧
d.栈帧内容包含:局部变量表、操作数栈、方法出口信息等
e.每个方法的调用过程,就是栈帧在虚拟机栈中入栈和出栈过程
2.2.表达式求值
a.假设有一个表达式:1+1024*1-1
b.计算机中,如何求解该表达式的值呢?
c.注意:当然不是人为口算
d.我们的目的是让计算机能够理解任意表达式
2.3.表达式求值过程
a.用两个栈实现表达式求值
b.一个用于存储数据:操作数栈
c.一个用于存储运算符:运算符栈
d.从左至右,读取表达式内容
e.如果是数据,入栈到操作数栈中
f.如果是运算符,入栈到运算符栈中
g.比较运算符的优先级
h.如果遇到高优先级的运算符,则将操作数栈的数据出栈
i.进行计算,把新的计算结果重新入栈到操作数栈
j.以此类推...直到处理完成整个表达式
jvm内存结构:

表达式求值过程:1+1024*1-1

来源:oschina
链接:https://my.oschina.net/u/4450329/blog/3179414