數據結構學習筆記之棧結構

數據結構-棧 學習筆記




棧結構:線性結構。從數據的存儲結構來進一步劃分,棧結構包括兩類:
        順序棧結構:使用一組地址連續的內存單元依次保存棧中的數據;
        鏈式棧結構:使用鏈表形式保存棧中各元素的值;

在棧結構中只能在一端進行操作,該操作端稱爲棧頂,另一端稱爲棧底。保存和取出數據都只能從棧結構的一端進行。
棧結構是按照"後進先出"的原則處理結點數據的。


圖1


Java實現的棧:
/**
 * 棧: 先進後出,後進先出 的線性表(LIFO). 限定僅在表尾進行插入和刪除操作的線性表.
 * 
 * @see java.util.ArrayDeque
 */
public class xStack<E> {

	Object[] elements;

	int bottom; // 棧底. index=0

	int top; // 棧頂.進行插入,刪除等操作.

	private static final int DEFAULT_INITIAL_CAPACITY = 1 << 3;

	private static final int MAX_CAPACITY = 1 << 16;

	/**
	 * 構造
	 */
	public xStack() {
		elements = new Object[DEFAULT_INITIAL_CAPACITY];
	}

	/**
	 * 構造
	 * 
	 * @param c
	 */
	public xStack(Collection<? extends E> c) {
		elements = new Object[calculateSize(c.size())];
		addAll(c);
	}

	/* 計算stack大小 */
	private int calculateSize(int capacity) {
		if (capacity < DEFAULT_INITIAL_CAPACITY)
			return DEFAULT_INITIAL_CAPACITY;
		return Math.min((int) Math.pow(2, capacity >> 2), MAX_CAPACITY);
	}

	/**
	 * 壓入若干個元素
	 * 
	 * @param c
	 * @return
	 */
	public boolean addAll(Collection<? extends E> c) {
		boolean modified = false;
		for (E e : c)
			if (add(e))
				modified = true;
		return modified;
	}

	/**
	 * 壓入一個元素
	 * 
	 * @param e
	 * @return
	 */
	public boolean add(E e) {
		Objects.requireNonNull(e);
		int length = elements.length - 1;
		if (top < length) {
			elements[top] = e;
			top++;
		} else if (top == length) {
			doubleCapacity(); // 擴容
			elements[top] = e;
			top++;
		}
		return true;
	}

	/* 擴容 */
	private void doubleCapacity() {
		int blank = elements.length;
		int newCapacity = Math.min(blank << 1, MAX_CAPACITY);
		if (newCapacity < 0)
			throw new IllegalStateException("xStack too big");
		Object[] o = new Object[newCapacity];
		System.arraycopy(elements, 0, o, 0, blank);
		elements = o;
	}

	/**
	 * 測試棧是否爲空
	 */
	public boolean isEmpty() {
		return bottom == top;
	}

	/**
	 * 查看棧頂,但不移除. 允許返回null
	 */
	@SuppressWarnings("unchecked")
	public E getTop() {
		return (E) elements[top - 1];
	}

	/**
	 * 從棧頂彈出一個元素(top).
	 */
	public E pop() {
		int h = top;
		@SuppressWarnings("unchecked")
		E result = (E) elements[h - 1];
		if (result == null)
			return null;
		elements[h - 1] = null;
		Object[] o = new Object[elements.length];
		System.arraycopy(elements, 0, o, 0, h);
		elements = o;
		top--;
		return result;
	}

	/**
	 * 將元素壓入棧頂(top).
	 */
	public void push(E e) {
		Objects.requireNonNull(e);
		int length = elements.length - 1;
		if (top < length) {
			elements[top] = e;
			top++;
		} else if (top == length) {
			doubleCapacity(); // 擴容
			elements[top] = e;
			top++;
		}
	}

	/**
	 * 返回元素在棧中的位置
	 */
	public int search(Object o) {
		if (o == null)
			return -1;
		int mask = elements.length - 1;
		Object obj = null;
		int i = bottom;
		while ((obj = elements[i]) != null) {
			if (o.equals(obj))
				return i;
			i = (i + 1) & mask;
		}
		return -1;
	}

	/**
	 * 返回棧的深度
	 */
	public int deep() {
		return (top - bottom) & (elements.length - 1);
	}

	/**
	 * 返回stack對象的字符串表示
	 */
	public String toString() {
		if (deep() == 0)
			return "[]";
		Object[] o = Arrays.copyOf(elements, deep());
		return Arrays.toString(o);
	}

}



注:


發佈了163 篇原創文章 · 獲贊 23 · 訪問量 29萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章