Java数据结构详解(十)-ArrayDeque

来源:互联网 发布:阿里云幕布可以ps吗 编辑:程序博客网 时间:2024/05/28 15:06

ArrayDeque

ArrayDeque是一个循环数组.只要数组不被填满,ArrayDeque就可以不用扩容.组的任何一点都可能被看作起点或者终点.

ArrayDeque是Deque 接口的大小可变数组的实现。数组双端队列没有容量限制;它们可根据需要增加以支持使用。它们不是线程安全的;在没有外部同步时,它们不支持多个线程的并发访问。禁止 null 元素。此类很可能在用作堆栈时快于 Stack,在用作队列时快于 LinkedList。

大多数 ArrayDeque 操作以摊销的固定时间运行。异常包括 remove、removeFirstOccurrence、removeLastOccurrence、contains、iterator.remove() 以及批量操作,它们均以线性时间运行。


ArrayDeque 字段

//底层数组transient Object[] elements; //头部指针transient int head;//尾部指针transient int tail;//初始化的最小容量private static final int MIN_INITIAL_CAPACITY = 8;

ArrayDeque 的构造方法

无参构造器

    public ArrayDeque() {        //构造一个空数组deque,初始容量足以容纳16个元素        elements = new Object[16];    }

有参数的构造器

    public ArrayDeque(int numElements) {        //构造一个空数组deque,初始容量足以容纳指定数量的元素        allocateElements(numElements);    }
    public ArrayDeque(Collection<? extends E> c) {        allocateElements(c.size());        addAll(c);    }

    private void allocateElements(int numElements) {        int initialCapacity = MIN_INITIAL_CAPACITY;        // Find the best power of two to hold elements.        // Tests "<=" because arrays aren't kept full.        if (numElements >= initialCapacity) {            initialCapacity = numElements;            initialCapacity |= (initialCapacity >>>  1);            initialCapacity |= (initialCapacity >>>  2);            initialCapacity |= (initialCapacity >>>  4);            initialCapacity |= (initialCapacity >>>  8);            initialCapacity |= (initialCapacity >>> 16);            initialCapacity++;            if (initialCapacity < 0)   // Too many elements, must back off                initialCapacity >>>= 1;// Good luck allocating 2 ^ 30 elements        }        elements = new Object[initialCapacity];    }

ArrayDeque 被用作队列时的方法

addLast(e)

    public void addLast(E e) {        //e为null时 抛出异常.        if (e == null)            throw new NullPointerException();        //在尾部位置添加e.        elements[tail] = e;        //下标是否越界        if ( (tail = (tail + 1) & (elements.length - 1)) == head)            //扩容            doubleCapacity();    }

offerLast(e)

    public boolean offerLast(E e) {        addLast(e);        return true;    }

pollFirst

    public E pollFirst() {        int h = head;        @SuppressWarnings("unchecked")        E result = (E) elements[h];        // Element is null if deque empty        if (result == null)            return null;        elements[h] = null;     // Must null out slot        head = (h + 1) & (elements.length - 1);        return result;    }

removeFirst()

    public E removeFirst() {        E x = pollFirst();        if (x == null)            throw new NoSuchElementException();        return x;    }

element()

    public E element() {        return getFirst();    }

peekFirst()

    @SuppressWarnings("unchecked")    public E peekFirst() {        // elements[head] is null if deque empty        return (E) elements[head];    }

peek

    public E peek() {        return peekFirst();    }

    //扩容方法,容量是原来的两倍    private void doubleCapacity() {        //保证Boolean表达式为 TRUE ,如果为FALSE则抛出异常;        assert head == tail;        int p = head;        int n = elements.length;        //计算head右边的元素个数        int r = n - p; // number of elements to the right of p        //newCapacity = n * 2  容量为原来的两倍        int newCapacity = n << 1;        if (newCapacity < 0)            throw new IllegalStateException("Sorry, deque too big");        new一个容量为原来数组容量两倍的新数组.        Object[] a = new Object[newCapacity];        //这里用了两次数组复制.目的是为了把原来的循环数组的数据展开.        System.arraycopy(elements, p, a, 0, r);        System.arraycopy(elements, 0, a, r, p);        elements = a;        head = 0;        tail = n;    }

ArrayDeque 被用作堆栈时的方法

push(e)

    public void push(E e) {        addFirst(e);    }

addFirst

    public void addFirst(E e) {        if (e == null)            throw new NullPointerException();        elements[head = (head - 1) & (elements.length - 1)] = e;        if (head == tail)            doubleCapacity();    }

pop()

    public E pop() {        return removeFirst();    }

removeFirst

    public E removeFirst() {        E x = pollFirst();        if (x == null)            throw new NoSuchElementException();        return x;    }

peek()

    public E peek() {        return peekFirst();    }

peekFirst()

    @SuppressWarnings("unchecked")    public E peekFirst() {        // elements[head] is null if deque empty        return (E) elements[head];    }
原创粉丝点击