棧是一個先進後出的數據結構,所以實現棧就抓住棧的該特性,當然使用數組實現棧,需要考慮擴容問題,如果使用鏈表來實現的話就沒有擴容問題了。
一、定義棧的方法接口
這裏定義了棧的幾個主要方法:
public interface IStack<E> {
/**
* 棧元素大小
* @return
*/
int size();
/**
* 是否爲空
* @return
*/
boolean empty();
/**
* 壓棧
* @param item
*/
void push(E item);
/**
* 彈棧
* @return
*/
E pop();
/**
* 查看棧頂元素
* @return
*/
E peek();
}
二、實現
/**
* 通過數組實現一個棧
* @param <E>
*/
public class ArrayStack<E> implements IStack<E> {
// 默認容量
private static final int DEFAULT_CAPACITY = 10;
// 保存元素的數組
private E[] data;
// 元素數量
private int size;
// 棧頂指針 索引
private int top;
public ArrayStack(){
this(DEFAULT_CAPACITY);
}
public ArrayStack(int capacity){
this.size = 0;
this.top = -1;
this.data = (E[]) new Object[capacity];
}
/**
* 棧元素大小
* @return
*/
@Override
public int size() {
return size;
}
/**
* 是否爲空
* @return
*/
@Override
public boolean empty() {
return size == 0;
}
/**
* 壓棧
* @param item
*/
@Override
public void push(E item) {
if(data.length == size){
// grow 擴容
grow(2 * size);
}
data[++top] = item;
size ++;
}
private void grow(int capacity){
if(capacity <= DEFAULT_CAPACITY )
return;
data = Arrays.copyOf(data, capacity);
}
/**
* 彈棧
* @return
*/
@Override
public E pop() {
if(size == 0){
throw new EmptyStackException();
}
size --;
if(size < (data.length>>1)){
grow(data.length>>1);
}
return data[top--];
}
/**
* 查看棧頂元素
* @return
*/
@Override
public E peek() {
if(size == 0){
throw new EmptyStackException();
}
return data[top];
}
public static void main(String[] args) {
IStack stack = new ArrayStack();
for(int i=0; i<10; i++){
stack.push(i+1);
}
System.out.println("彈出元素:"+stack.pop());
System.out.println("彈出元素:"+stack.pop());
for (int i = 0; i < 8; i++) {
System.out.println("彈出剩餘元素:"+stack.pop());
}
}
}
測試結果:
彈出元素:10
彈出元素:9
彈出剩餘元素:8
彈出剩餘元素:7
彈出剩餘元素:6
彈出剩餘元素:5
彈出剩餘元素:4
彈出剩餘元素:3
彈出剩餘元素:2
彈出剩餘元素:1