栈是一种“后进先出(LIFO)”的数据结构,最后压入的数据项总是位于栈顶的位置,下面是维基百科中对栈的定义:
堆栈(英语:stack),也可直接称栈。台湾作堆叠,在计算机科学中,是一种特殊的串行形式的数据结构,它的特殊之处在于只能允许在链结串行或阵列的一端(称为堆叠顶端指标,英语:top)进行加入资料(英语:push)和输出资料(英语:pop)的运算。另外堆叠也可以用一维阵列或连结串行的形式来完成。堆叠的另外一个相对的操作方式称为伫列。
由于堆叠数据结构只允许在一端进行操作,因而按照后进先出(LIFO, Last In First Out)的原理运作。
堆叠数据结构使用两种基本操作:推入(push)和弹出(pop):
- 推入:将数据放入堆叠的顶端(阵列形式或串行形式),堆叠顶端top指标加一。
- 弹出:将顶端数据资料输出(回传),堆叠顶端资料减一。
实际应用:
a、在我们熟悉的图形化界面编程中,例如那种撤销操作,撤销最近一次执行的操作,大多数情况下就是使用栈这种特殊的数据结构来实现的,当然使用其他的方式也可以实现。
b、可以实现对一个字符串进行反转操作,当然这里是可以实现,但是并不推荐这样去做,实际上直接使用数组反序输出更加方便快捷,效率也更高。
1、首先我们先定义一个Stack Interface,我们把他定义成泛型的.
package com.stack;
/**
* 栈接口
* @author feizi
* @time 2015-1-12下午3:23:32
*/
public interface StackInterface<E> {
//获取堆栈长度
public int size();
//入栈
public void push(E element) throws Exception;
//出栈
public E pop() throws Exception;
//获取栈顶元素
public E peek() throws Exception;
//获取栈中元素个数
public int getElementCount();
//判断是否当前栈顶指针没有到达栈底
public boolean hasMoreElement();
//判断栈空
public boolean isEmpty();
//判断栈溢
public boolean isFull();
//清空栈
public void clear();
}
2、然后,利用数组实现堆栈,
package com.stack;
import java.util.Arrays;
/**
* 栈接口的具体实现类
* @author feizi
* @time 2015-1-12下午3:44:36
*/
public class ArrayStack<E> implements StackInterface<E> {
private final int DEFAULT_SIZE = 3;//堆栈初始化时缺省大小
private int maxSize;//堆栈的最大容量
private E[] arrayObj;//数组
private int top;//栈顶指针
@SuppressWarnings("unchecked")
public ArrayStack(){
this.maxSize = DEFAULT_SIZE;
this.arrayObj = (E[]) new Object[this.maxSize];
top = -1;
}
@SuppressWarnings("unchecked")
public ArrayStack(int size){
this.maxSize = size;
this.arrayObj = (E[]) new Object[this.maxSize];
top = -1;
}
/**
* 获取堆栈长度
* @return
*/
public int size(){
return this.maxSize;
}
/**
* 获取堆栈中元素个数
*/
public int getElementCount() {
return this.top;
}
/**
* 入栈,
* @throws Exception
*/
public void push(E element) throws Exception {
if(null == element){
throw new Exception("入栈的元素不能为空!");
}
if(isFull()){
//如果栈满,就扩容
extendSize();
//或者如果不想扩容的话,可以在此处抛出异常
//throw new Exception("栈满不能入栈!");
}
this.arrayObj[++top] = element;
}
/**
* 出栈
* @throws Exception
*/
public E pop() throws Exception {
if(isEmpty()){
throw new Exception("栈空不能出栈");
}
//先保存栈顶元素
E element = (E) arrayObj[top];
//然后清空栈顶元素
arrayObj[top] = null;
//栈顶指针下移,栈中元素减少一个
top--;
return element;
//或者
// return (E) this.arrayObj[top--];
}
/**
* 获取栈顶元素,先判空
* @throws Exception
*/
public E peek() throws Exception {
if(isEmpty()){
throw new Exception("栈为空!");
}
return (E) this.arrayObj[getElementCount()];
}
/**
* 判断是否当前栈顶指针没有到达栈底
*/
public boolean hasMoreElement() {
return getElementCount() >= 0 ? true : false;
}
/**
* 扩容,通常是在栈满以后才会扩充
*/
@SuppressWarnings("unchecked")
public void extendSize(){
this.maxSize = this.maxSize + this.DEFAULT_SIZE;
Object[] newArray = new Object[this.maxSize];
//使用java.lang包中提供的system.arrcopy()方法复制数组
System.arraycopy(arrayObj, 0, newArray, 0, arrayObj.length);
//将原数组置空
Arrays.fill(arrayObj, null);
this.arrayObj = (E[]) newArray;
}
/**
* 判断栈空
*/
public boolean isEmpty() {
return this.top == -1;
}
/**
* 判断栈溢
*/
public boolean isFull() {
return this.top + 1 == this.maxSize;
}
/**
* 清空栈
*/
@SuppressWarnings("unchecked")
public void clear() {
//将数组置空
Arrays.fill(arrayObj, null);
//栈顶指针重置
this.top = -1;
this.maxSize = this.DEFAULT_SIZE;
this.arrayObj = (E[]) new Object[this.maxSize];
}
public static void main(String[] args) throws Exception {
StackInterface<Object> myStack = new ArrayStack<Object>();
System.out.println("==栈的总容量:"+myStack.size());
System.out.println("==堆栈的元素个数:"+myStack.getElementCount());
myStack.push(1);
myStack.push("root");
myStack.push(2);
myStack.push(3);
myStack.push("admin");
myStack.push(4);
myStack.push("feizi");
System.out.println("==栈的总容量:"+myStack.size());
System.out.println("==堆栈的元素个数:"+myStack.getElementCount());
System.out.println("栈顶元素为:"+myStack.peek());
while (myStack.hasMoreElement()) {
System.out.println("栈指针:"+myStack.getElementCount()+",栈元素:"+myStack.pop());
}
//清空栈
myStack.clear();
System.out.println("==栈的总容量:"+myStack.size());
System.out.println("==堆栈的元素个数:"+myStack.getElementCount());
while (myStack.hasMoreElement()) {
System.out.println("================栈顶元素为:"+myStack.peek());
System.out.println("栈指针:"+myStack.getElementCount()+",栈元素:"+myStack.pop());
}
}
}