数据结构(2)--- 栈和队列

一、栈

1.栈(Stack)的概念:

    栈是一种只能在一端进行插入和删除操作的特殊线性表,它按照先进先出的原则存储数据,先进的被放在栈低,后进的被放在栈顶,我们需要去数据的时候都是从栈顶弹出数据。

2.栈的原理实现:

  思路:数组有一个最大有效数据的个数,每次添加或者删除数据这个变量都会随之改变,每次添加数据都是在最大有效数据的后面位置增加数据,删除数据是把最后一条数据设置为null,最大有效数据减一,获取数据都是获取最大有效长度那个数据,长度不够一般是把长度左移一位(<<1)乘以2的1次方。

  代码:

package stack;

import java.util.Arrays;

/**
 * 栈--原理
 * Created by bigfly on 2018/7/17.
 */
public class MyStack {

    /**
     * 用来记录修改次数
     * 由于线程不安全
     * 每次修改的时候modCount++
     * 当迭代的时候先把modCount 赋值给迭代器的exceptedModCount,
     * 在做增删改时候判断modCount与exceptedModCount是否相等,
     * 如果相等,代表没有第二个线程在迭代过程中增删改了数据,
     * 如果不相等,代表有第二个线程在迭代的过程中操作了数据,这个时候就会抛出ConcurrentModificationException
     * 这个就是fast-fail(快速失败)机制
     */
    int modCount = 0;
    /**
     * 用来记录有效(非null)数据的个数
     * 作用:
     */
    protected int elementCount;
    /**
     * 主要用来存放数据的
     */
    protected Object[] elementData;

    /**
     * 空参构造器
     */
    public MyStack(){
        elementData = new Object[10];

    };
    /**
     *拿到栈顶数据
     */
    public Object peek(){
        int len = size();
        //每次拿的是有效长度位置的数据
        Object obj = elementData[len-1];
        return obj;
    }

    /**
     *移除栈顶数据并返回该数据
     */
    public Object pop(){
        Object obj;
        //拿到栈顶数据
        obj = peek();
        //记录操作一次
        modCount++;
        //有效数据减少一个
        elementCount--;
        //让最后一个位置变成null
        //因为peek()  是拿到有效长度位置的数据,所以把最后一个数变成null下一次也不会取到
        elementData[elementCount] = null;
        return obj;
    }

    /**
     * 添加数据到栈顶 数组最后添加数据
     */
    public Object push(Object obj){
        if(elementCount+1 > elementData.length){
            //扩容
            elementData = Arrays.copyOf(elementData,elementData.length<<1);
        }
        elementData[elementCount] = obj;
        elementCount++;
        modCount++;
        return obj;
    }

    /**
     * 从栈顶向下查找,找出第一次出现该数据的是第几个
     */
    public Integer search(Object o){
        if(o==null){
            for(int i = elementCount-1 ; i > -1 ; i--){
                if(elementData[i]==null){
                    return elementCount-i;
                }
            }
        }else{
            for(int i = elementCount-1 ; i > -1 ; i--){
                if(o.equals(elementData[i])){
                    return elementCount-i;
                }
            }
        }
        return -1;
    }



    /**
     * 返回有效数据的个数
     * @return
     */
    public synchronized int size() {
        return elementCount;
    }


    @Override
    public String toString() {
        StringBuffer a = new StringBuffer();
        for (int i = 0; i < elementData.length; i++) {
            a.append(elementData[i]);
            a.append(",");
        }
        return a.toString();
    }
}

3.栈的效率:

  数据的入栈出栈的时间复杂度都是O(1),也就是说,栈的操作耗时不依赖栈中数据项的个数,因此操作时间很短。栈不需要比较和移动的操作。

二、队列:

1.队列(queue)的概念:

  队列只允许在一端插入,在另一端删除,所以最早添加的数据最先从列队中删除,所以列队又成为先进先出线性表

  队列可以分为:

    ①:单项队列:只能在一端添加数据,另外一端删除数据。

    ②:双向队列:每一端都可以添加和删除数据。

    ③:优先队列:数据按照关键字大小排序,插入数据都会插入合适的位置保证有序。          

  

猜你喜欢

转载自www.cnblogs.com/bigfly277/p/9325406.html