copyonwritearraylist.java

来自「用applet实现很多应用小程序」· Java 代码 · 共 1,242 行 · 第 1/4 页

JAVA
1,242
字号
        Object[] elements = getArray();
        int len = elements.length;
        if (len != 0) {
            // temp array holds those elements we know we want to keep
            int newlen = 0;
            Object[] temp = new Object[len];
            for (int i = 0; i < len; ++i) {
                Object element = elements[i];
                if (c.contains(element))
                    temp[newlen++] = element;
            }
            if (newlen != len) {
                setArray(copyOfRange(temp, 0, newlen, Object[].class));
                return true;
            }
        }
        return false;
    }

    /**
     * Appends all of the elements in the specified collection that
     * are not already contained in this list, to the end of
     * this list, in the order that they are returned by the
     * specified collection's iterator.
     *
     * @param c collection containing elements to be added to this list
     * @return the number of elements added
     * @throws NullPointerException if the specified collection is null
     * @see #addIfAbsent(Object)
     */
    public int addAllAbsent(Collection c) {
        int numNew = c.size();
        if (numNew == 0)
            return 0;
        synchronized (this) {
            Object[] elements = getArray();
            int len = elements.length;

            Object[] temp = new Object[numNew];
            int added = 0;
            for (Iterator itr = c.iterator(); itr.hasNext(); ) {
                Object e = itr.next();
                if (indexOf(e, elements, 0, len) < 0 &&
                    indexOf(e, temp, 0, added) < 0)
                    temp[added++] = e;
            }
            if (added != 0) {
                Object[] newElements = new Object[len + added];
                System.arraycopy(elements, 0, newElements, 0, len);
                System.arraycopy(temp, 0, newElements, len, added);
                setArray(newElements);
            }
            return added;
        }
    }

    /**
     * Removes all of the elements from this list.
     * The list will be empty after this call returns.
     */
    public synchronized void clear() {
        setArray(new Object[0]);
    }

    /**
     * Appends all of the elements in the specified collection to the end
     * of this list, in the order that they are returned by the specified
     * collection's iterator.
     *
     * @param c collection containing elements to be added to this list
     * @return <tt>true</tt> if this list changed as a result of the call
     * @throws NullPointerException if the specified collection is null
     * @see #add(Object)
     */
    public boolean addAll(Collection c) {
        int numNew = c.size();
        if (numNew == 0)
            return false;
        synchronized (this) {
            Object[] elements = getArray();
            int len = elements.length;
            Object[] newElements = new Object[len + numNew];
            System.arraycopy(elements, 0, newElements, 0, len);
            for (Iterator itr = c.iterator(); itr.hasNext(); ) {
                Object e = itr.next();
                newElements[len++] = e;
            }
            setArray(newElements);
            return true;
        }
    }

    /**
     * Inserts all of the elements in the specified collection into this
     * list, starting at the specified position.  Shifts the element
     * currently at that position (if any) and any subsequent elements to
     * the right (increases their indices).  The new elements will appear
     * in this list in the order that they are returned by the
     * specified collection's iterator.
     *
     * @param index index at which to insert the first element
     *        from the specified collection
     * @param c collection containing elements to be added to this list
     * @return <tt>true</tt> if this list changed as a result of the call
     * @throws IndexOutOfBoundsException {@inheritDoc}
     * @throws NullPointerException if the specified collection is null
     * @see #add(int,Object)
     */
    public boolean addAll(int index, Collection c) {
        int numNew = c.size();
        synchronized (this) {
            Object[] elements = getArray();
            int len = elements.length;
            if (index > len || index < 0)
                throw new IndexOutOfBoundsException("Index: " + index +
                                                    ", Size: "+ len);
            if (numNew == 0)
                return false;
            int numMoved = len - index;
            Object[] newElements;
            if (numMoved == 0)
                newElements = copyOf(elements, len + numNew);
            else {
                newElements = new Object[len + numNew];
                System.arraycopy(elements, 0, newElements, 0, index);
                System.arraycopy(elements, index,
                                 newElements, index + numNew,
                                 numMoved);
            }
            for (Iterator itr = c.iterator(); itr.hasNext(); ) {
                Object e = itr.next();
                newElements[index++] = e;
            }
            setArray(newElements);
            return true;
        }
    }

    /**
     * Save the state of the list to a stream (i.e., serialize it).
     *
     * @serialData The length of the array backing the list is emitted
     *               (int), followed by all of its elements (each an Object)
     *               in the proper order.
     * @param s the stream
     */
    private void writeObject(java.io.ObjectOutputStream s)
        throws java.io.IOException{

        // Write out element count, and any hidden stuff
        s.defaultWriteObject();

        Object[] elements = getArray();
        int len = elements.length;
        // Write out array length
        s.writeInt(len);

        // Write out all elements in the proper order.
        for (int i = 0; i < len; i++)
            s.writeObject(elements[i]);
    }

    /**
     * Reconstitute the list from a stream (i.e., deserialize it).
     * @param s the stream
     */
    private void readObject(java.io.ObjectInputStream s)
        throws java.io.IOException, ClassNotFoundException {

        // Read in size, and any hidden stuff
        s.defaultReadObject();

        // Read in array length and allocate array
        int len = s.readInt();
        Object[] elements = new Object[len];

        // Read in all elements in the proper order.
        for (int i = 0; i < len; i++)
            elements[i] = s.readObject();
        setArray(elements);

    }

    /**
     * Returns a string representation of this list, containing
     * the String representation of each element.
     */
    public String toString() {
        Object[] elements = getArray();
        int maxIndex = elements.length - 1;
        StringBuffer buf = new StringBuffer();
        buf.append("[");
        for (int i = 0; i <= maxIndex; i++) {
            buf.append(String.valueOf(elements[i]));
            if (i < maxIndex)
                buf.append(", ");
        }
        buf.append("]");
        return buf.toString();
    }

    /**
     * Compares the specified object with this list for equality.
     * Returns true if and only if the specified object is also a {@link
     * List}, both lists have the same size, and all corresponding pairs
     * of elements in the two lists are <em>equal</em>.  (Two elements
     * <tt>e1</tt> and <tt>e2</tt> are <em>equal</em> if <tt>(e1==null ?
     * e2==null : e1.equals(e2))</tt>.)  In other words, two lists are
     * defined to be equal if they contain the same elements in the same
     * order.
     *
     * @param o the object to be compared for equality with this list
     * @return <tt>true</tt> if the specified object is equal to this list
     */
    public boolean equals(Object o) {
        if (o == this)
            return true;
        if (!(o instanceof List))
            return false;

        List l2 = (List)(o);
        if (size() != l2.size())
            return false;

        ListIterator e1 = listIterator();
        ListIterator e2 = l2.listIterator();
        while (e1.hasNext()) {
            if (!eq(e1.next(), e2.next()))
                return false;
        }
        return true;
    }

    /**
     * Returns the hash code value for this list.
     *
     * <p>This implementation uses the definition in {@link List#hashCode}.
     *
     * @return the hash code value for this list
     */
    public int hashCode() {
        int hashCode = 1;
        Object[] elements = getArray();
        int len = elements.length;
        for (int i = 0; i < len; ++i) {
            Object obj = elements[i];
            hashCode = 31*hashCode + (obj==null ? 0 : obj.hashCode());
        }
        return hashCode;
    }

    /**
     * Returns an iterator over the elements in this list in proper sequence.
     *
     * <p>The returned iterator provides a snapshot of the state of the list
     * when the iterator was constructed. No synchronization is needed while
     * traversing the iterator. The iterator does <em>NOT</em> support the
     * <tt>remove</tt> method.
     *
     * @return an iterator over the elements in this list in proper sequence
     */
    public Iterator iterator() {
        return new COWIterator(getArray(), 0);
    }

    /**
     * {@inheritDoc}
     *
     * <p>The returned iterator provides a snapshot of the state of the list
     * when the iterator was constructed. No synchronization is needed while
     * traversing the iterator. The iterator does <em>NOT</em> support the
     * <tt>remove</tt>, <tt>set</tt> or <tt>add</tt> methods.
     */
    public ListIterator listIterator() {
        return new COWIterator(getArray(), 0);
    }

    /**
     * {@inheritDoc}
     *
     * <p>The list iterator returned by this implementation will throw an
     * <tt>UnsupportedOperationException</tt> in its <tt>remove</tt>,
     * <tt>set</tt> and <tt>add</tt> methods.
     *
     * @throws IndexOutOfBoundsException {@inheritDoc}
     */
    public ListIterator listIterator(final int index) {
        Object[] elements = getArray();
        int len = elements.length;
        if (index < 0 || index > len)
            throw new IndexOutOfBoundsException("Index: " + index);

        return new COWIterator(getArray(), index);
    }

    private static class COWIterator implements ListIterator {
        /** Snapshot of the array **/
        private final Object[] snapshot;
        /** Index of element to be returned by subsequent call to next.  */
        private int cursor;

        private COWIterator(Object[] elements, int initialCursor) {
            cursor = initialCursor;
            snapshot = elements;
        }

        public boolean hasNext() {
            return cursor < snapshot.length;
        }

        public boolean hasPrevious() {

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?