顺序栈,链式栈,JDK自带的原生栈

顺序栈,链式栈,JDK自带的原生栈

  1. 堆栈(英语:stack)又称为栈或堆叠,是计算机科学中的一种抽象资料类型,只允许在有序的线性资料集合的一端(称为堆栈顶端,英语:top)进行加入数据(英语:push)和移除数据(英语:pop)的运算。因而按照后进先出(LIFO, Last In First Out)的原理运作。

  2. 堆栈使用两种基本操作:推入(压栈,push)和弹出(弹栈,pop):

    推入:将资料放入堆栈顶端,堆栈顶端移到新放入的资料。
    弹出:将堆栈顶端资料移除,堆栈顶端移到移除后的下一笔资料

  3. 堆栈的基本特点:

    先入后出,后入先出。
    除头尾节点之外,每个元素有一个前驱,一个后继。

顺序栈

  1. 所谓顺序栈,就是使用数组实现栈
  2. 实现代码
//使用数组实现顺序栈
class ArrayStackDemo{
    //使用数组实现栈,栈的特点先进后出
    private Object[] res;
    //栈中元素个数
    private int count;
    //栈的大小
    private int n;

    //初始化栈
    public ArrayStackDemo(int n){
        this.n = n;
        this.res = new Object[n];
        this.count = 0;
    }

    //判断栈是否为空
    public boolean isEmpty(){
        return count == 0;
    }

    //判断栈是否已满
    public boolean isFull(){
        return count == n;
    }

    //入栈
    public void push(Object object){
        //添加之前判断栈是否已满
        if (!isFull()){
            res[count] = object;
            count++;
        }
    }

    //出栈
    public Object pop(){
        //出栈前首先判断栈是否为空
        Object object = null;
        if (!isEmpty()){
           object = res[count - 1];
           count--;
        }
        return object;
    }

    //弹出栈顶元素
    public Object peek(){
        //出栈前首先判断栈是否为空
        Object object = null;
        if (!isEmpty()){
            object = res[count - 1];
        }
        return object;
    }
}

链式栈

  1. 所谓链式栈就是使用链来实现栈
  2. 代码如下
//使用链表实现链式栈
class ListStackDemo{
    //基于链表实现栈

    //数据结点node,单链表表结构
    private static class Node{
        private Object data;
        private Node next;

        public Node(Object data, Node next) {
            this.data = data;
            this.next = next;
        }

        public Object getData() {
            return data;
        }
    }

    //虚拟链表头部
    private Node top = null;
    //判断栈中是否出栈元素
    public boolean isEmpty(){
        return top == null;
    }

    //入栈方法
    public void push(Object object){
        Node newNode = new Node(object,null);
        if (isEmpty()){
            top = newNode;
        }else {
            //头插法,形成一个先进后出的效果
            newNode.next = top;
            top = newNode;
        }
    }

    //出栈方法
    public Object pop(){
        if (top == null) return null;
        Object object = top.data;
        top = top.next;
        return object;
    }
}

JDK自带的原生栈

  1. 下面我们来看看JDK自带的原生栈(JDK1.8)
/**
 1. The <code>Stack</code> class represents a last-in-first-out
 2. (LIFO) stack of objects. It extends class <tt>Vector</tt> with five
 3. operations that allow a vector to be treated as a stack. The usual
 4. <tt>push</tt> and <tt>pop</tt> operations are provided, as well as a
 5. method to <tt>peek</tt> at the top item on the stack, a method to test
 6. for whether the stack is <tt>empty</tt>, and a method to <tt>search</tt>
 7. the stack for an item and discover how far it is from the top.
 8. <p>
 9. When a stack is first created, it contains no items.
 10.  11. <p>A more complete and consistent set of LIFO stack operations is
 12. provided by the {@link Deque} interface and its implementations, which
 13. should be used in preference to this class.  For example:
 14. <pre>   {@code
 15.   Deque<Integer> stack = new ArrayDeque<Integer>();}</pre>
 16.  17. @author  Jonathan Payne
 18. @since   JDK1.0
 */
public
class Stack<E> extends Vector<E> {
    /**
     * Creates an empty Stack.
     */
    public Stack() {
    }

    /**
     * Pushes an item onto the top of this stack. This has exactly
     * the same effect as:
     * <blockquote><pre>
     * addElement(item)</pre></blockquote>
     *
     * @param   item   the item to be pushed onto this stack.
     * @return  the <code>item</code> argument.
     * @see     java.util.Vector#addElement
     */
    public E push(E item) {
        addElement(item);

        return item;
    }

    /**
     * Removes the object at the top of this stack and returns that
     * object as the value of this function.
     *
     * @return  The object at the top of this stack (the last item
     *          of the <tt>Vector</tt> object).
     * @throws  EmptyStackException  if this stack is empty.
     */
    public synchronized E pop() {
        E       obj;
        int     len = size();

        obj = peek();
        removeElementAt(len - 1);

        return obj;
    }

    /**
     * Looks at the object at the top of this stack without removing it
     * from the stack.
     *
     * @return  the object at the top of this stack (the last item
     *          of the <tt>Vector</tt> object).
     * @throws  EmptyStackException  if this stack is empty.
     */
    public synchronized E peek() {
        int     len = size();

        if (len == 0)
            throw new EmptyStackException();
        return elementAt(len - 1);
    }

    /**
     * Tests if this stack is empty.
     *
     * @return  <code>true</code> if and only if this stack contains
     *          no items; <code>false</code> otherwise.
     */
    public boolean empty() {
        return size() == 0;
    }

    /**
     * Returns the 1-based position where an object is on this stack.
     * If the object <tt>o</tt> occurs as an item in this stack, this
     * method returns the distance from the top of the stack of the
     * occurrence nearest the top of the stack; the topmost item on the
     * stack is considered to be at distance <tt>1</tt>. The <tt>equals</tt>
     * method is used to compare <tt>o</tt> to the
     * items in this stack.
     *
     * @param   o   the desired object.
     * @return  the 1-based position from the top of the stack where
     *          the object is located; the return value <code>-1</code>
     *          indicates that the object is not on the stack.
     */
    public synchronized int search(Object o) {
        int i = lastIndexOf(o);

        if (i >= 0) {
            return size() - i;
        }
        return -1;
    }

    /** use serialVersionUID from JDK 1.0.2 for interoperability */
    private static final long serialVersionUID = 1224463164541339165L;
}
  1. JDK1.8中自带的栈是继承于Vector实现的,Vector 是 List 的古老实现类,底层使用Object[ ] 存储,线程安全的。他的push和pop中实际调用的Vector的addElement和removeElementAt方法
public synchronized void addElement(E obj) {
        modCount++;
        ensureCapacityHelper(elementCount + 1);
        elementData[elementCount++] = obj;
    }

当栈容量不足时,会触发扩容机制

    private void ensureCapacityHelper(int minCapacity) {
        // overflow-conscious code
        if (minCapacity - elementData.length > 0)
            grow(minCapacity);
    }
    private void grow(int minCapacity) {
        // overflow-conscious code
        int oldCapacity = elementData.length;
        int newCapacity = oldCapacity + ((capacityIncrement > 0) ?
                                         capacityIncrement : oldCapacity);
        if (newCapacity - minCapacity < 0)
            newCapacity = minCapacity;
        if (newCapacity - MAX_ARRAY_SIZE > 0)
            newCapacity = hugeCapacity(minCapacity);
        elementData = Arrays.copyOf(elementData, newCapacity);
    }

removeElementAt方法

    public synchronized void removeElementAt(int index) {
        modCount++;
        if (index >= elementCount) {
            throw new ArrayIndexOutOfBoundsException(index + " >= " +
                                                     elementCount);
        }
        else if (index < 0) {
            throw new ArrayIndexOutOfBoundsException(index);
        }
        int j = elementCount - index - 1;
        if (j > 0) {
            System.arraycopy(elementData, index + 1, elementData, index, j);
        }
        elementCount--;
        elementData[elementCount] = null; /* to let gc do its work */
    }
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值