概要
学完 Vector 了之后, 接下来我们开始学习 Stack.Stack 很简单, 它继承于 Vector. 学习方式还是和之前一样, 先对 Stack 有个整体认识, 然后再学习它的源码; 最后再通过实例来学会使用它.
第 1 部分 Stack 介绍
Stack 简介
Stack 是栈. 它的特性是: 先进后出(FILO, First In Last Out).
java 工具包中的 Stack 是继承于 Vector(矢量队列)的, 由于 Vector 是通过数组实现的, 这就意味着, Stack 也是通过数组实现的, 而非链表. 当然, 我们也可以将 LinkedList 当作栈来使用! 在 "Java 集合系列 06 之 Vector 详细介绍 (源码解析) 和使用示例" 中, 已经详细介绍过 Vector 的数据结构, 这里就不再对 Stack 的数据结构进行说明了.
Stack 的继承关系
- java.lang.Object
- ? java.util.AbstractCollection<E>
- ? java.util.AbstractList<E>
- ? java.util.Vector<E>
- ? java.util.Stack<E>
- public class Stack<E> extends Vector<E> {}
Stack 和 Collection 的关系如下图:
Stack 的构造函数
Stack 只有一个默认构造函数, 如下:
Stack()
Stack 的 API
Stack 是栈, 它常用的 API 如下:
- boolean empty()
- synchronized E peek()
- synchronized E pop()
- E push(E object)
- synchronized int search(Object o)
由于 Stack 和继承于 Vector, 因此它也包含 Vector 中的全部 API.
第 2 部分 Stack 源码解析(基于 JDK1.6.0_45)
Stack 的源码非常简单, 下面我们对它进行学习.
- package java.util;
- public
- class Stack<E> extends Vector<E> {
- // 版本 ID. 这个用于版本升级控制, 这里不须理会!
- private static final long serialVersionUID = 1224463164541339165L;
- // 构造函数
- public Stack() {
- }
- // push 函数: 将元素存入栈顶
- public E push(E item) {
- // 将元素存入栈顶.
- // addElement()的实现在 Vector.java 中
- addElement(item);
- return item;
- }
- // pop 函数: 返回栈顶元素, 并将其从栈中删除
- public synchronized E pop() {
- E obj;
- int len = size();
- obj = peek();
- // 删除栈顶元素, removeElementAt()的实现在 Vector.java 中
- removeElementAt(len - 1);
- return obj;
- }
- // peek 函数: 返回栈顶元素, 不执行删除操作
- public synchronized E peek() {
- int len = size();
- if (len == 0)
- throw new EmptyStackException();
- // 返回栈顶元素, elementAt()具体实现在 Vector.java 中
- return elementAt(len - 1);
- }
- // 栈是否为空
- public boolean empty() {
- return size() == 0;
- }
- // 查找 "元素 o" 在栈中的位置: 由栈底向栈顶方向数
- public synchronized int search(Object o) {
- // 获取元素索引, elementAt()具体实现在 Vector.java 中
- int i = lastIndexOf(o);
- if (i>= 0) {
- return size() - i;
- }
- return -1;
- }
- }
总结:
(01) Stack 实际上也是通过数组去实现的.
执行 push 时(即, 将元素推入栈中), 是通过将元素追加的数组的末尾中.
执行 peek 时(即, 取出栈顶元素, 不执行删除), 是返回数组末尾的元素.
执行 pop 时(即, 取出栈顶元素, 并将该元素从栈中删除), 是取出数组末尾的元素, 然后将该元素从数组中删除.
(02) Stack 继承于 Vector, 意味着 Vector 拥有的属性和功能, Stack 都拥有.
第 3 部分 Vector 示例
下面我们通过实例学习如何使用 Stack
- import java.util.Stack;
- import java.util.Iterator;
- import java.util.List;
- /**
- * @desc Stack 的测试程序. 测试常用 API 的用法
- *
- * @author skywang
- */
- public class StackTest {
- public static void main(String[] args) {
- Stack stack = new Stack();
- // 将 1,2,3,4,5 添加到栈中
- for(int i=1; i<6; i++) {
- stack.push(String.valueOf(i));
- }
- // 遍历并打印出该栈
- iteratorThroughRandomAccess(stack) ;
- // 查找 "2" 在栈中的位置, 并输出
- int pos = stack.search("2");
- System.out.println("the postion of 2 is:"+pos);
- // pup 栈顶元素之后, 遍历栈
- stack.pop();
- iteratorThroughRandomAccess(stack) ;
- // peek 栈顶元素之后, 遍历栈
- String val = (String)stack.peek();
- System.out.println("peek:"+val);
- iteratorThroughRandomAccess(stack) ;
- // 通过 Iterator 去遍历 Stack
- iteratorThroughIterator(stack) ;
- }
- /**
- * 通过快速访问遍历 Stack
- */
- public static void iteratorThroughRandomAccess(List list) {
- String val = null;
- for (int i=0; i<list.size(); i++) {
- val = (String)list.get(i);
- System.out.print(val+" ");
- }
- System.out.println();
- }
- /**
- * 通过迭代器遍历 Stack
- */
- public static void iteratorThroughIterator(List list) {
- String val = null;
- for(Iterator iter = list.iterator(); iter.hasNext(); ) {
- val = (String)iter.next();
- System.out.print(val+" ");
- }
- System.out.println();
- }
- }
运行结果:
- 1 2 3 4 5
- the postion of 2 is:4
- 1 2 3 4
- peek:4
- 1 2 3 4
- 1 2 3 4
来源: http://www.bubuko.com/infodetail-2604717.html