数据结构学习—— 栈(stack)java
栈(stack)是一种运算受限的线性数据结构,运算受限指的是栈这种数据结构仅容许在一端添加元素,删除元素,这一端被称做栈顶,相对应的另外一端则称为栈底。如图所示:
git
当咱们在文档编辑器中输入文字,当发现输入错误时,想要撤销到前一步,这个操做就是Undo。撤销的原理实际上就是栈这种数据结构来设计实现的。例如:李雷在某个文档编辑器上输入文字“我爱韩梅梅”,结果,因为李雷满脑子想的都是韩梅梅的音容笑貌,不当心将内容输入成了“我爱含梅梅”。李雷想将内容恢复到“我爱” 这一步,因此他按了三次“Ctrl+z”,而后又依次将“韩”,“梅”,“梅”三个字输入了进去。
github
来看一个C语言的问题:算法
#include<stdio.h>
int main(void){
int i=1;
printf("%d%d%d",i,i++,i++);
return 0;
}
复制代码
这个程序的运行结果是什么?若是只是知道i++与++i的区别是不足以解决这道问题的。先公布答案,这个程序的运行结果为:321,这与printf的底层原理有关,由于printf的底层实现就是栈。仍是拿李雷韩梅梅来举例说明。数组
printf("我爱韩梅梅");
复制代码
printf函数首先会将字符串内容从右至左 push到栈中。bash
有以下程序:数据结构
A();
function A(){
1 ...
2 B();
3 ...
4 end
}
function B(){
1 ...
2 C();
3 ...
4 end
}
function C(){
1 ...
2 ...
3 ...
4 end
}
复制代码
程序从A方法开始调用,执行到 A方法的第二行,计算机发现须要执行B方法,这时就会将执行到哪一步这样一个信息压入到系统栈中。例如,定义A2为A方法的第二行,计算机此时将A2压入系统栈,代表执行到了A方法的第二行。
编辑器
本文中ArrayStack的底层实现数组为动态数组:动态数组,DobbyKim's Blog。
函数
public interface Stack<E> {
void push(E e);
E pop();
E peek();
int getSize();
boolean isEmpty();
}
public class ArrayStack<E> implements Stack<E>{
Array<E> array;
public ArrayStack(int capacity){
array = new Array<>(capacity);
}
public ArrayStack(){
array = new Array<>();
}
public void push(E e){...}
public E pop(){...}
public int getSize(){...}
public int getCapacity(){...}
public boolean isEmpty(){...}
public E peek(){...}
public String toString(){...}
}
复制代码
点击查看源码
ArrayStack的方法push 与 pop 的均摊时间复杂度为O(1),由于这里面涉及到底层实现Array为动态数组,resize()扩容操做为一个O(n)的算法。getSize()方法,peek()方法,isEmpty()方法的时间复杂度均为O(1)。学习
给定一个只包括 '(',')','{','}','[',']' 的字符串,判断字符串是否有效。
有效字符串需知足:
左括号必须用相同类型的右括号闭合。
左括号必须以正确的顺序闭合。
注意空字符串可被认为是有效字符串。
输入: "()"
输出: true
复制代码
输入: "()[]{}"
输出: true
复制代码
输入: "(]"
输出: false
复制代码
输入: "([)]"
输出: false
复制代码
输入: "{[]}"
输出: true
复制代码
问题解决思路:栈。只要是左侧的括号为'(','[','{'就push到栈中,遇到与之匹配的右侧括号则pop,最后栈若是为空则说明匹配成功。Java代码以下:
import java.util.Stack
class Solution {
public boolean isValid(String s) {
Stack<Character>stack = new Stack<>();
for(int i=0;i<s.length();i++){
if(s.charAt(i)=='(' || s.charAt(i)=='[' || s.charAt(i)=='{'){
stack.push(s.charAt(i));
}else{
if(stack.isEmpty())
return false;
char c = stack.pop;
if(s.charAt(i)==')' && c!='(')
return false;
if(s.charAt(i)==']' && c!='[')
return false;
if(s.charAt(i)=='}' && c!='{')
return false;
}
}
return stack.isEmpty();
}
}
复制代码