1 /*
   2  * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 package java.util;
  27 
  28 import java.util.function.Consumer;
  29 import java.util.function.Predicate;
  30 import java.util.function.UnaryOperator;
  31 import sun.misc.SharedSecrets;
  32 
  33 /**
  34  * Resizable-array implementation of the <tt>List</tt> interface.  Implements
  35  * all optional list operations, and permits all elements, including
  36  * <tt>null</tt>.  In addition to implementing the <tt>List</tt> interface,
  37  * this class provides methods to manipulate the size of the array that is
  38  * used internally to store the list.  (This class is roughly equivalent to
  39  * <tt>Vector</tt>, except that it is unsynchronized.)
  40  *
  41  * <p>The <tt>size</tt>, <tt>isEmpty</tt>, <tt>get</tt>, <tt>set</tt>,
  42  * <tt>iterator</tt>, and <tt>listIterator</tt> operations run in constant
  43  * time.  The <tt>add</tt> operation runs in <i>amortized constant time</i>,
  44  * that is, adding n elements requires O(n) time.  All of the other operations
  45  * run in linear time (roughly speaking).  The constant factor is low compared
  46  * to that for the <tt>LinkedList</tt> implementation.
  47  *
  48  * <p>Each <tt>ArrayList</tt> instance has a <i>capacity</i>.  The capacity is
  49  * the size of the array used to store the elements in the list.  It is always
  50  * at least as large as the list size.  As elements are added to an ArrayList,
  51  * its capacity grows automatically.  The details of the growth policy are not
  52  * specified beyond the fact that adding an element has constant amortized
  53  * time cost.
  54  *
  55  * <p>An application can increase the capacity of an <tt>ArrayList</tt> instance
  56  * before adding a large number of elements using the <tt>ensureCapacity</tt>
  57  * operation.  This may reduce the amount of incremental reallocation.
  58  *
  59  * <p><strong>Note that this implementation is not synchronized.</strong>
  60  * If multiple threads access an <tt>ArrayList</tt> instance concurrently,
  61  * and at least one of the threads modifies the list structurally, it
  62  * <i>must</i> be synchronized externally.  (A structural modification is
  63  * any operation that adds or deletes one or more elements, or explicitly
  64  * resizes the backing array; merely setting the value of an element is not
  65  * a structural modification.)  This is typically accomplished by
  66  * synchronizing on some object that naturally encapsulates the list.
  67  *
  68  * If no such object exists, the list should be "wrapped" using the
  69  * {@link Collections#synchronizedList Collections.synchronizedList}
  70  * method.  This is best done at creation time, to prevent accidental
  71  * unsynchronized access to the list:<pre>
  72  *   List list = Collections.synchronizedList(new ArrayList(...));</pre>
  73  *
  74  * <p><a name="fail-fast">
  75  * The iterators returned by this class's {@link #iterator() iterator} and
  76  * {@link #listIterator(int) listIterator} methods are <em>fail-fast</em>:</a>
  77  * if the list is structurally modified at any time after the iterator is
  78  * created, in any way except through the iterator's own
  79  * {@link ListIterator#remove() remove} or
  80  * {@link ListIterator#add(Object) add} methods, the iterator will throw a
  81  * {@link ConcurrentModificationException}.  Thus, in the face of
  82  * concurrent modification, the iterator fails quickly and cleanly, rather
  83  * than risking arbitrary, non-deterministic behavior at an undetermined
  84  * time in the future.
  85  *
  86  * <p>Note that the fail-fast behavior of an iterator cannot be guaranteed
  87  * as it is, generally speaking, impossible to make any hard guarantees in the
  88  * presence of unsynchronized concurrent modification.  Fail-fast iterators
  89  * throw {@code ConcurrentModificationException} on a best-effort basis.
  90  * Therefore, it would be wrong to write a program that depended on this
  91  * exception for its correctness:  <i>the fail-fast behavior of iterators
  92  * should be used only to detect bugs.</i>
  93  *
  94  * <p>This class is a member of the
  95  * <a href="{@docRoot}/../technotes/guides/collections/index.html">
  96  * Java Collections Framework</a>.
  97  *
  98  * @author  Josh Bloch
  99  * @author  Neal Gafter
 100  * @see     Collection
 101  * @see     List
 102  * @see     LinkedList
 103  * @see     Vector
 104  * @since   1.2
 105  */
 106 
 107 public class ArrayList<E> extends AbstractList<E>
 108         implements List<E>, RandomAccess, Cloneable, java.io.Serializable
 109 {
 110     private static final long serialVersionUID = 8683452581122892189L;
 111 
 112     /**
 113      * Default initial capacity.
 114      */
 115     private static final int DEFAULT_CAPACITY = 10;
 116 
 117     /**
 118      * Shared empty array instance used for empty instances.
 119      */
 120     private static final Object[] EMPTY_ELEMENTDATA = {};
 121 
 122     /**
 123      * Shared empty array instance used for default sized empty instances. We
 124      * distinguish this from EMPTY_ELEMENTDATA to know how much to inflate when
 125      * first element is added.
 126      */
 127     private static final Object[] DEFAULTCAPACITY_EMPTY_ELEMENTDATA = {};
 128 
 129     /**
 130      * The array buffer into which the elements of the ArrayList are stored.
 131      * The capacity of the ArrayList is the length of this array buffer. Any
 132      * empty ArrayList with elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA
 133      * will be expanded to DEFAULT_CAPACITY when the first element is added.
 134      */
 135     transient Object[] elementData; // non-private to simplify nested class access
 136 
 137     /**
 138      * The size of the ArrayList (the number of elements it contains).
 139      *
 140      * @serial
 141      */
 142     private int size;
 143 
 144     /**
 145      * Constructs an empty list with the specified initial capacity.
 146      *
 147      * @param  initialCapacity  the initial capacity of the list
 148      * @throws IllegalArgumentException if the specified initial capacity
 149      *         is negative
 150      */
 151     public ArrayList(int initialCapacity) {
 152         if (initialCapacity > 0) {
 153             this.elementData = new Object[initialCapacity];
 154         } else if (initialCapacity == 0) {
 155             this.elementData = EMPTY_ELEMENTDATA;
 156         } else {
 157             throw new IllegalArgumentException("Illegal Capacity: "+
 158                                                initialCapacity);
 159         }
 160     }
 161 
 162     /**
 163      * Constructs an empty list with an initial capacity of ten.
 164      */
 165     public ArrayList() {
 166         this.elementData = DEFAULTCAPACITY_EMPTY_ELEMENTDATA;
 167     }
 168 
 169     /**
 170      * Constructs a list containing the elements of the specified
 171      * collection, in the order they are returned by the collection's
 172      * iterator.
 173      *
 174      * @param c the collection whose elements are to be placed into this list
 175      * @throws NullPointerException if the specified collection is null
 176      */
 177     public ArrayList(Collection<? extends E> c) {
 178         elementData = c.toArray();
 179         if ((size = elementData.length) != 0) {
 180             // c.toArray might (incorrectly) not return Object[] (see 6260652)
 181             if (elementData.getClass() != Object[].class)
 182                 elementData = Arrays.copyOf(elementData, size, Object[].class);
 183         } else {
 184             // replace with empty array.
 185             this.elementData = EMPTY_ELEMENTDATA;
 186         }
 187     }
 188 
 189     /**
 190      * Trims the capacity of this <tt>ArrayList</tt> instance to be the
 191      * list's current size.  An application can use this operation to minimize
 192      * the storage of an <tt>ArrayList</tt> instance.
 193      */
 194     public void trimToSize() {
 195         modCount++;
 196         if (size < elementData.length) {
 197             elementData = (size == 0)
 198               ? EMPTY_ELEMENTDATA
 199               : Arrays.copyOf(elementData, size);
 200         }
 201     }
 202 
 203     /**
 204      * Increases the capacity of this <tt>ArrayList</tt> instance, if
 205      * necessary, to ensure that it can hold at least the number of elements
 206      * specified by the minimum capacity argument.
 207      *
 208      * @param   minCapacity   the desired minimum capacity
 209      */
 210     public void ensureCapacity(int minCapacity) {
 211         int minExpand = (elementData != DEFAULTCAPACITY_EMPTY_ELEMENTDATA)
 212             // any size if not default element table
 213             ? 0
 214             // larger than default for default empty table. It's already
 215             // supposed to be at default size.
 216             : DEFAULT_CAPACITY;
 217 
 218         if (minCapacity > minExpand) {
 219             ensureExplicitCapacity(minCapacity);
 220         }
 221     }
 222 
 223     private static int calculateCapacity(Object[] elementData, int minCapacity) {
 224         if (elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA) {
 225             return Math.max(DEFAULT_CAPACITY, minCapacity);
 226         }
 227         return minCapacity;
 228     }
 229 
 230     private void ensureCapacityInternal(int minCapacity) {
 231         ensureExplicitCapacity(calculateCapacity(elementData, minCapacity));
 232     }
 233 
 234     private void ensureExplicitCapacity(int minCapacity) {
 235         modCount++;
 236 
 237         // overflow-conscious code
 238         if (minCapacity - elementData.length > 0)
 239             grow(minCapacity);
 240     }
 241 
 242     /**
 243      * The maximum size of array to allocate.
 244      * Some VMs reserve some header words in an array.
 245      * Attempts to allocate larger arrays may result in
 246      * OutOfMemoryError: Requested array size exceeds VM limit
 247      */
 248     private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;
 249 
 250     /**
 251      * Increases the capacity to ensure that it can hold at least the
 252      * number of elements specified by the minimum capacity argument.
 253      *
 254      * @param minCapacity the desired minimum capacity
 255      */
 256     private void grow(int minCapacity) {
 257         // overflow-conscious code
 258         int oldCapacity = elementData.length;
 259         int newCapacity = oldCapacity + (oldCapacity >> 1);
 260         if (newCapacity - minCapacity < 0)
 261             newCapacity = minCapacity;
 262         if (newCapacity - MAX_ARRAY_SIZE > 0)
 263             newCapacity = hugeCapacity(minCapacity);
 264         // minCapacity is usually close to size, so this is a win:
 265         elementData = Arrays.copyOf(elementData, newCapacity);
 266     }
 267 
 268     private static int hugeCapacity(int minCapacity) {
 269         if (minCapacity < 0) // overflow
 270             throw new OutOfMemoryError();
 271         return (minCapacity > MAX_ARRAY_SIZE) ?
 272             Integer.MAX_VALUE :
 273             MAX_ARRAY_SIZE;
 274     }
 275 
 276     /**
 277      * Returns the number of elements in this list.
 278      *
 279      * @return the number of elements in this list
 280      */
 281     public int size() {
 282         return size;
 283     }
 284 
 285     /**
 286      * Returns <tt>true</tt> if this list contains no elements.
 287      *
 288      * @return <tt>true</tt> if this list contains no elements
 289      */
 290     public boolean isEmpty() {
 291         return size == 0;
 292     }
 293 
 294     /**
 295      * Returns <tt>true</tt> if this list contains the specified element.
 296      * More formally, returns <tt>true</tt> if and only if this list contains
 297      * at least one element <tt>e</tt> such that
 298      * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>.
 299      *
 300      * @param o element whose presence in this list is to be tested
 301      * @return <tt>true</tt> if this list contains the specified element
 302      */
 303     public boolean contains(Object o) {
 304         return indexOf(o) >= 0;
 305     }
 306 
 307     /**
 308      * Returns the index of the first occurrence of the specified element
 309      * in this list, or -1 if this list does not contain the element.
 310      * More formally, returns the lowest index <tt>i</tt> such that
 311      * <tt>(o==null&nbsp;?&nbsp;get(i)==null&nbsp;:&nbsp;o.equals(get(i)))</tt>,
 312      * or -1 if there is no such index.
 313      */
 314     public int indexOf(Object o) {
 315         if (o == null) {
 316             for (int i = 0; i < size; i++)
 317                 if (elementData[i]==null)
 318                     return i;
 319         } else {
 320             for (int i = 0; i < size; i++)
 321                 if (o.equals(elementData[i]))
 322                     return i;
 323         }
 324         return -1;
 325     }
 326 
 327     /**
 328      * Returns the index of the last occurrence of the specified element
 329      * in this list, or -1 if this list does not contain the element.
 330      * More formally, returns the highest index <tt>i</tt> such that
 331      * <tt>(o==null&nbsp;?&nbsp;get(i)==null&nbsp;:&nbsp;o.equals(get(i)))</tt>,
 332      * or -1 if there is no such index.
 333      */
 334     public int lastIndexOf(Object o) {
 335         if (o == null) {
 336             for (int i = size-1; i >= 0; i--)
 337                 if (elementData[i]==null)
 338                     return i;
 339         } else {
 340             for (int i = size-1; i >= 0; i--)
 341                 if (o.equals(elementData[i]))
 342                     return i;
 343         }
 344         return -1;
 345     }
 346 
 347     /**
 348      * Returns a shallow copy of this <tt>ArrayList</tt> instance.  (The
 349      * elements themselves are not copied.)
 350      *
 351      * @return a clone of this <tt>ArrayList</tt> instance
 352      */
 353     public Object clone() {
 354         try {
 355             ArrayList<?> v = (ArrayList<?>) super.clone();
 356             v.elementData = Arrays.copyOf(elementData, size);
 357             v.modCount = 0;
 358             return v;
 359         } catch (CloneNotSupportedException e) {
 360             // this shouldn't happen, since we are Cloneable
 361             throw new InternalError(e);
 362         }
 363     }
 364 
 365     /**
 366      * Returns an array containing all of the elements in this list
 367      * in proper sequence (from first to last element).
 368      *
 369      * <p>The returned array will be "safe" in that no references to it are
 370      * maintained by this list.  (In other words, this method must allocate
 371      * a new array).  The caller is thus free to modify the returned array.
 372      *
 373      * <p>This method acts as bridge between array-based and collection-based
 374      * APIs.
 375      *
 376      * @return an array containing all of the elements in this list in
 377      *         proper sequence
 378      */
 379     public Object[] toArray() {
 380         return Arrays.copyOf(elementData, size);
 381     }
 382 
 383     /**
 384      * Returns an array containing all of the elements in this list in proper
 385      * sequence (from first to last element); the runtime type of the returned
 386      * array is that of the specified array.  If the list fits in the
 387      * specified array, it is returned therein.  Otherwise, a new array is
 388      * allocated with the runtime type of the specified array and the size of
 389      * this list.
 390      *
 391      * <p>If the list fits in the specified array with room to spare
 392      * (i.e., the array has more elements than the list), the element in
 393      * the array immediately following the end of the collection is set to
 394      * <tt>null</tt>.  (This is useful in determining the length of the
 395      * list <i>only</i> if the caller knows that the list does not contain
 396      * any null elements.)
 397      *
 398      * @param a the array into which the elements of the list are to
 399      *          be stored, if it is big enough; otherwise, a new array of the
 400      *          same runtime type is allocated for this purpose.
 401      * @return an array containing the elements of the list
 402      * @throws ArrayStoreException if the runtime type of the specified array
 403      *         is not a supertype of the runtime type of every element in
 404      *         this list
 405      * @throws NullPointerException if the specified array is null
 406      */
 407     @SuppressWarnings("unchecked")
 408     public <T> T[] toArray(T[] a) {
 409         if (a.length < size)
 410             // Make a new array of a's runtime type, but my contents:
 411             return (T[]) Arrays.copyOf(elementData, size, a.getClass());
 412         System.arraycopy(elementData, 0, a, 0, size);
 413         if (a.length > size)
 414             a[size] = null;
 415         return a;
 416     }
 417 
 418     // Positional Access Operations
 419 
 420     @SuppressWarnings("unchecked")
 421     E elementData(int index) {
 422         return (E) elementData[index];
 423     }
 424 
 425     /**
 426      * Returns the element at the specified position in this list.
 427      *
 428      * @param  index index of the element to return
 429      * @return the element at the specified position in this list
 430      * @throws IndexOutOfBoundsException {@inheritDoc}
 431      */
 432     public E get(int index) {
 433         rangeCheck(index);
 434 
 435         return elementData(index);
 436     }
 437 
 438     /**
 439      * Replaces the element at the specified position in this list with
 440      * the specified element.
 441      *
 442      * @param index index of the element to replace
 443      * @param element element to be stored at the specified position
 444      * @return the element previously at the specified position
 445      * @throws IndexOutOfBoundsException {@inheritDoc}
 446      */
 447     public E set(int index, E element) {
 448         rangeCheck(index);
 449 
 450         E oldValue = elementData(index);
 451         elementData[index] = element;
 452         return oldValue;
 453     }
 454 
 455     /**
 456      * Appends the specified element to the end of this list.
 457      *
 458      * @param e element to be appended to this list
 459      * @return <tt>true</tt> (as specified by {@link Collection#add})
 460      */
 461     public boolean add(E e) {
 462         ensureCapacityInternal(size + 1);  // Increments modCount!!
 463         elementData[size++] = e;
 464         return true;
 465     }
 466 
 467     /**
 468      * Inserts the specified element at the specified position in this
 469      * list. Shifts the element currently at that position (if any) and
 470      * any subsequent elements to the right (adds one to their indices).
 471      *
 472      * @param index index at which the specified element is to be inserted
 473      * @param element element to be inserted
 474      * @throws IndexOutOfBoundsException {@inheritDoc}
 475      */
 476     public void add(int index, E element) {
 477         rangeCheckForAdd(index);
 478 
 479         ensureCapacityInternal(size + 1);  // Increments modCount!!
 480         System.arraycopy(elementData, index, elementData, index + 1,
 481                          size - index);
 482         elementData[index] = element;
 483         size++;
 484     }
 485 
 486     /**
 487      * Removes the element at the specified position in this list.
 488      * Shifts any subsequent elements to the left (subtracts one from their
 489      * indices).
 490      *
 491      * @param index the index of the element to be removed
 492      * @return the element that was removed from the list
 493      * @throws IndexOutOfBoundsException {@inheritDoc}
 494      */
 495     public E remove(int index) {
 496         rangeCheck(index);
 497 
 498         modCount++;
 499         E oldValue = elementData(index);
 500 
 501         int numMoved = size - index - 1;
 502         if (numMoved > 0)
 503             System.arraycopy(elementData, index+1, elementData, index,
 504                              numMoved);
 505         elementData[--size] = null; // clear to let GC do its work
 506 
 507         return oldValue;
 508     }
 509 
 510     /**
 511      * Removes the first occurrence of the specified element from this list,
 512      * if it is present.  If the list does not contain the element, it is
 513      * unchanged.  More formally, removes the element with the lowest index
 514      * <tt>i</tt> such that
 515      * <tt>(o==null&nbsp;?&nbsp;get(i)==null&nbsp;:&nbsp;o.equals(get(i)))</tt>
 516      * (if such an element exists).  Returns <tt>true</tt> if this list
 517      * contained the specified element (or equivalently, if this list
 518      * changed as a result of the call).
 519      *
 520      * @param o element to be removed from this list, if present
 521      * @return <tt>true</tt> if this list contained the specified element
 522      */
 523     public boolean remove(Object o) {
 524         if (o == null) {
 525             for (int index = 0; index < size; index++)
 526                 if (elementData[index] == null) {
 527                     fastRemove(index);
 528                     return true;
 529                 }
 530         } else {
 531             for (int index = 0; index < size; index++)
 532                 if (o.equals(elementData[index])) {
 533                     fastRemove(index);
 534                     return true;
 535                 }
 536         }
 537         return false;
 538     }
 539 
 540     /*
 541      * Private remove method that skips bounds checking and does not
 542      * return the value removed.
 543      */
 544     private void fastRemove(int index) {
 545         modCount++;
 546         int numMoved = size - index - 1;
 547         if (numMoved > 0)
 548             System.arraycopy(elementData, index+1, elementData, index,
 549                              numMoved);
 550         elementData[--size] = null; // clear to let GC do its work
 551     }
 552 
 553     /**
 554      * Removes all of the elements from this list.  The list will
 555      * be empty after this call returns.
 556      */
 557     public void clear() {
 558         modCount++;
 559 
 560         // clear to let GC do its work
 561         for (int i = 0; i < size; i++)
 562             elementData[i] = null;
 563 
 564         size = 0;
 565     }
 566 
 567     /**
 568      * Appends all of the elements in the specified collection to the end of
 569      * this list, in the order that they are returned by the
 570      * specified collection's Iterator.  The behavior of this operation is
 571      * undefined if the specified collection is modified while the operation
 572      * is in progress.  (This implies that the behavior of this call is
 573      * undefined if the specified collection is this list, and this
 574      * list is nonempty.)
 575      *
 576      * @param c collection containing elements to be added to this list
 577      * @return <tt>true</tt> if this list changed as a result of the call
 578      * @throws NullPointerException if the specified collection is null
 579      */
 580     public boolean addAll(Collection<? extends E> c) {
 581         Object[] a = c.toArray();
 582         int numNew = a.length;
 583         ensureCapacityInternal(size + numNew);  // Increments modCount
 584         System.arraycopy(a, 0, elementData, size, numNew);
 585         size += numNew;
 586         return numNew != 0;
 587     }
 588 
 589     /**
 590      * Inserts all of the elements in the specified collection into this
 591      * list, starting at the specified position.  Shifts the element
 592      * currently at that position (if any) and any subsequent elements to
 593      * the right (increases their indices).  The new elements will appear
 594      * in the list in the order that they are returned by the
 595      * specified collection's iterator.
 596      *
 597      * @param index index at which to insert the first element from the
 598      *              specified collection
 599      * @param c collection containing elements to be added to this list
 600      * @return <tt>true</tt> if this list changed as a result of the call
 601      * @throws IndexOutOfBoundsException {@inheritDoc}
 602      * @throws NullPointerException if the specified collection is null
 603      */
 604     public boolean addAll(int index, Collection<? extends E> c) {
 605         rangeCheckForAdd(index);
 606 
 607         Object[] a = c.toArray();
 608         int numNew = a.length;
 609         ensureCapacityInternal(size + numNew);  // Increments modCount
 610 
 611         int numMoved = size - index;
 612         if (numMoved > 0)
 613             System.arraycopy(elementData, index, elementData, index + numNew,
 614                              numMoved);
 615 
 616         System.arraycopy(a, 0, elementData, index, numNew);
 617         size += numNew;
 618         return numNew != 0;
 619     }
 620 
 621     /**
 622      * Removes from this list all of the elements whose index is between
 623      * {@code fromIndex}, inclusive, and {@code toIndex}, exclusive.
 624      * Shifts any succeeding elements to the left (reduces their index).
 625      * This call shortens the list by {@code (toIndex - fromIndex)} elements.
 626      * (If {@code toIndex==fromIndex}, this operation has no effect.)
 627      *
 628      * @throws IndexOutOfBoundsException if {@code fromIndex} or
 629      *         {@code toIndex} is out of range
 630      *         ({@code fromIndex < 0 ||
 631      *          fromIndex >= size() ||
 632      *          toIndex > size() ||
 633      *          toIndex < fromIndex})
 634      */
 635     protected void removeRange(int fromIndex, int toIndex) {
 636         modCount++;
 637         int numMoved = size - toIndex;
 638         System.arraycopy(elementData, toIndex, elementData, fromIndex,
 639                          numMoved);
 640 
 641         // clear to let GC do its work
 642         int newSize = size - (toIndex-fromIndex);
 643         for (int i = newSize; i < size; i++) {
 644             elementData[i] = null;
 645         }
 646         size = newSize;
 647     }
 648 
 649     /**
 650      * Checks if the given index is in range.  If not, throws an appropriate
 651      * runtime exception.  This method does *not* check if the index is
 652      * negative: It is always used immediately prior to an array access,
 653      * which throws an ArrayIndexOutOfBoundsException if index is negative.
 654      */
 655     private void rangeCheck(int index) {
 656         if (index >= size)
 657             throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
 658     }
 659 
 660     /**
 661      * A version of rangeCheck used by add and addAll.
 662      */
 663     private void rangeCheckForAdd(int index) {
 664         if (index > size || index < 0)
 665             throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
 666     }
 667 
 668     /**
 669      * Constructs an IndexOutOfBoundsException detail message.
 670      * Of the many possible refactorings of the error handling code,
 671      * this "outlining" performs best with both server and client VMs.
 672      */
 673     private String outOfBoundsMsg(int index) {
 674         return "Index: "+index+", Size: "+size;
 675     }
 676 
 677     /**
 678      * Removes from this list all of its elements that are contained in the
 679      * specified collection.
 680      *
 681      * @param c collection containing elements to be removed from this list
 682      * @return {@code true} if this list changed as a result of the call
 683      * @throws ClassCastException if the class of an element of this list
 684      *         is incompatible with the specified collection
 685      * (<a href="Collection.html#optional-restrictions">optional</a>)
 686      * @throws NullPointerException if this list contains a null element and the
 687      *         specified collection does not permit null elements
 688      * (<a href="Collection.html#optional-restrictions">optional</a>),
 689      *         or if the specified collection is null
 690      * @see Collection#contains(Object)
 691      */
 692     public boolean removeAll(Collection<?> c) {
 693         Objects.requireNonNull(c);
 694         return batchRemove(c, false);
 695     }
 696 
 697     /**
 698      * Retains only the elements in this list that are contained in the
 699      * specified collection.  In other words, removes from this list all
 700      * of its elements that are not contained in the specified collection.
 701      *
 702      * @param c collection containing elements to be retained in this list
 703      * @return {@code true} if this list changed as a result of the call
 704      * @throws ClassCastException if the class of an element of this list
 705      *         is incompatible with the specified collection
 706      * (<a href="Collection.html#optional-restrictions">optional</a>)
 707      * @throws NullPointerException if this list contains a null element and the
 708      *         specified collection does not permit null elements
 709      * (<a href="Collection.html#optional-restrictions">optional</a>),
 710      *         or if the specified collection is null
 711      * @see Collection#contains(Object)
 712      */
 713     public boolean retainAll(Collection<?> c) {
 714         Objects.requireNonNull(c);
 715         return batchRemove(c, true);
 716     }
 717 
 718     private boolean batchRemove(Collection<?> c, boolean complement) {
 719         final Object[] elementData = this.elementData;
 720         int r = 0, w = 0;
 721         boolean modified = false;
 722         try {
 723             for (; r < size; r++)
 724                 if (c.contains(elementData[r]) == complement)
 725                     elementData[w++] = elementData[r];
 726         } finally {
 727             // Preserve behavioral compatibility with AbstractCollection,
 728             // even if c.contains() throws.
 729             if (r != size) {
 730                 System.arraycopy(elementData, r,
 731                                  elementData, w,
 732                                  size - r);
 733                 w += size - r;
 734             }
 735             if (w != size) {
 736                 // clear to let GC do its work
 737                 for (int i = w; i < size; i++)
 738                     elementData[i] = null;
 739                 modCount += size - w;
 740                 size = w;
 741                 modified = true;
 742             }
 743         }
 744         return modified;
 745     }
 746 
 747     /**
 748      * Save the state of the <tt>ArrayList</tt> instance to a stream (that
 749      * is, serialize it).
 750      *
 751      * @serialData The length of the array backing the <tt>ArrayList</tt>
 752      *             instance is emitted (int), followed by all of its elements
 753      *             (each an <tt>Object</tt>) in the proper order.
 754      */
 755     private void writeObject(java.io.ObjectOutputStream s)
 756         throws java.io.IOException{
 757         // Write out element count, and any hidden stuff
 758         int expectedModCount = modCount;
 759         s.defaultWriteObject();
 760 
 761         // Write out size as capacity for behavioural compatibility with clone()
 762         s.writeInt(size);
 763 
 764         // Write out all elements in the proper order.
 765         for (int i=0; i<size; i++) {
 766             s.writeObject(elementData[i]);
 767         }
 768 
 769         if (modCount != expectedModCount) {
 770             throw new ConcurrentModificationException();
 771         }
 772     }
 773 
 774     /**
 775      * Reconstitute the <tt>ArrayList</tt> instance from a stream (that is,
 776      * deserialize it).
 777      */
 778     private void readObject(java.io.ObjectInputStream s)
 779         throws java.io.IOException, ClassNotFoundException {
 780         elementData = EMPTY_ELEMENTDATA;
 781 
 782         // Read in size, and any hidden stuff
 783         s.defaultReadObject();
 784 
 785         // Read in capacity
 786         s.readInt(); // ignored
 787 
 788         if (size > 0) {
 789             // be like clone(), allocate array based upon size not capacity
 790             int capacity = calculateCapacity(elementData, size);
 791             SharedSecrets.getJavaOISAccess().checkArray(s, Object[].class, capacity);
 792             ensureCapacityInternal(size);
 793 
 794             Object[] a = elementData;
 795             // Read in all elements in the proper order.
 796             for (int i=0; i<size; i++) {
 797                 a[i] = s.readObject();
 798             }
 799         }
 800     }
 801 
 802     /**
 803      * Returns a list iterator over the elements in this list (in proper
 804      * sequence), starting at the specified position in the list.
 805      * The specified index indicates the first element that would be
 806      * returned by an initial call to {@link ListIterator#next next}.
 807      * An initial call to {@link ListIterator#previous previous} would
 808      * return the element with the specified index minus one.
 809      *
 810      * <p>The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
 811      *
 812      * @throws IndexOutOfBoundsException {@inheritDoc}
 813      */
 814     public ListIterator<E> listIterator(int index) {
 815         if (index < 0 || index > size)
 816             throw new IndexOutOfBoundsException("Index: "+index);
 817         return new ListItr(index);
 818     }
 819 
 820     /**
 821      * Returns a list iterator over the elements in this list (in proper
 822      * sequence).
 823      *
 824      * <p>The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
 825      *
 826      * @see #listIterator(int)
 827      */
 828     public ListIterator<E> listIterator() {
 829         return new ListItr(0);
 830     }
 831 
 832     /**
 833      * Returns an iterator over the elements in this list in proper sequence.
 834      *
 835      * <p>The returned iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
 836      *
 837      * @return an iterator over the elements in this list in proper sequence
 838      */
 839     public Iterator<E> iterator() {
 840         return new Itr();
 841     }
 842 
 843     /**
 844      * An optimized version of AbstractList.Itr
 845      */
 846     private class Itr implements Iterator<E> {
 847         int cursor;       // index of next element to return
 848         int lastRet = -1; // index of last element returned; -1 if no such
 849         int expectedModCount = modCount;
 850 
 851         public boolean hasNext() {
 852             return cursor != size;
 853         }
 854 
 855         @SuppressWarnings("unchecked")
 856         public E next() {
 857             checkForComodification();
 858             int i = cursor;
 859             if (i >= size)
 860                 throw new NoSuchElementException();
 861             Object[] elementData = ArrayList.this.elementData;
 862             if (i >= elementData.length)
 863                 throw new ConcurrentModificationException();
 864             cursor = i + 1;
 865             return (E) elementData[lastRet = i];
 866         }
 867 
 868         public void remove() {
 869             if (lastRet < 0)
 870                 throw new IllegalStateException();
 871             checkForComodification();
 872 
 873             try {
 874                 ArrayList.this.remove(lastRet);
 875                 cursor = lastRet;
 876                 lastRet = -1;
 877                 expectedModCount = modCount;
 878             } catch (IndexOutOfBoundsException ex) {
 879                 throw new ConcurrentModificationException();
 880             }
 881         }
 882 
 883         @Override
 884         @SuppressWarnings("unchecked")
 885         public void forEachRemaining(Consumer<? super E> consumer) {
 886             Objects.requireNonNull(consumer);
 887             final int size = ArrayList.this.size;
 888             int i = cursor;
 889             if (i >= size) {
 890                 return;
 891             }
 892             final Object[] elementData = ArrayList.this.elementData;
 893             if (i >= elementData.length) {
 894                 throw new ConcurrentModificationException();
 895             }
 896             while (i != size && modCount == expectedModCount) {
 897                 consumer.accept((E) elementData[i++]);
 898             }
 899             // update once at end of iteration to reduce heap write traffic
 900             cursor = i;
 901             lastRet = i - 1;
 902             checkForComodification();
 903         }
 904 
 905         final void checkForComodification() {
 906             if (modCount != expectedModCount)
 907                 throw new ConcurrentModificationException();
 908         }
 909     }
 910 
 911     /**
 912      * An optimized version of AbstractList.ListItr
 913      */
 914     private class ListItr extends Itr implements ListIterator<E> {
 915         ListItr(int index) {
 916             super();
 917             cursor = index;
 918         }
 919 
 920         public boolean hasPrevious() {
 921             return cursor != 0;
 922         }
 923 
 924         public int nextIndex() {
 925             return cursor;
 926         }
 927 
 928         public int previousIndex() {
 929             return cursor - 1;
 930         }
 931 
 932         @SuppressWarnings("unchecked")
 933         public E previous() {
 934             checkForComodification();
 935             int i = cursor - 1;
 936             if (i < 0)
 937                 throw new NoSuchElementException();
 938             Object[] elementData = ArrayList.this.elementData;
 939             if (i >= elementData.length)
 940                 throw new ConcurrentModificationException();
 941             cursor = i;
 942             return (E) elementData[lastRet = i];
 943         }
 944 
 945         public void set(E e) {
 946             if (lastRet < 0)
 947                 throw new IllegalStateException();
 948             checkForComodification();
 949 
 950             try {
 951                 ArrayList.this.set(lastRet, e);
 952             } catch (IndexOutOfBoundsException ex) {
 953                 throw new ConcurrentModificationException();
 954             }
 955         }
 956 
 957         public void add(E e) {
 958             checkForComodification();
 959 
 960             try {
 961                 int i = cursor;
 962                 ArrayList.this.add(i, e);
 963                 cursor = i + 1;
 964                 lastRet = -1;
 965                 expectedModCount = modCount;
 966             } catch (IndexOutOfBoundsException ex) {
 967                 throw new ConcurrentModificationException();
 968             }
 969         }
 970     }
 971 
 972     /**
 973      * Returns a view of the portion of this list between the specified
 974      * {@code fromIndex}, inclusive, and {@code toIndex}, exclusive.  (If
 975      * {@code fromIndex} and {@code toIndex} are equal, the returned list is
 976      * empty.)  The returned list is backed by this list, so non-structural
 977      * changes in the returned list are reflected in this list, and vice-versa.
 978      * The returned list supports all of the optional list operations.
 979      *
 980      * <p>This method eliminates the need for explicit range operations (of
 981      * the sort that commonly exist for arrays).  Any operation that expects
 982      * a list can be used as a range operation by passing a subList view
 983      * instead of a whole list.  For example, the following idiom
 984      * removes a range of elements from a list:
 985      * <pre>
 986      *      list.subList(from, to).clear();
 987      * </pre>
 988      * Similar idioms may be constructed for {@link #indexOf(Object)} and
 989      * {@link #lastIndexOf(Object)}, and all of the algorithms in the
 990      * {@link Collections} class can be applied to a subList.
 991      *
 992      * <p>The semantics of the list returned by this method become undefined if
 993      * the backing list (i.e., this list) is <i>structurally modified</i> in
 994      * any way other than via the returned list.  (Structural modifications are
 995      * those that change the size of this list, or otherwise perturb it in such
 996      * a fashion that iterations in progress may yield incorrect results.)
 997      *
 998      * @throws IndexOutOfBoundsException {@inheritDoc}
 999      * @throws IllegalArgumentException {@inheritDoc}
1000      */
1001     public List<E> subList(int fromIndex, int toIndex) {
1002         subListRangeCheck(fromIndex, toIndex, size);
1003         return new SubList(this, 0, fromIndex, toIndex);
1004     }
1005 
1006     static void subListRangeCheck(int fromIndex, int toIndex, int size) {
1007         if (fromIndex < 0)
1008             throw new IndexOutOfBoundsException("fromIndex = " + fromIndex);
1009         if (toIndex > size)
1010             throw new IndexOutOfBoundsException("toIndex = " + toIndex);
1011         if (fromIndex > toIndex)
1012             throw new IllegalArgumentException("fromIndex(" + fromIndex +
1013                                                ") > toIndex(" + toIndex + ")");
1014     }
1015 
1016     private class SubList extends AbstractList<E> implements RandomAccess {
1017         private final AbstractList<E> parent;
1018         private final int parentOffset;
1019         private final int offset;
1020         int size;
1021 
1022         SubList(AbstractList<E> parent,
1023                 int offset, int fromIndex, int toIndex) {
1024             this.parent = parent;
1025             this.parentOffset = fromIndex;
1026             this.offset = offset + fromIndex;
1027             this.size = toIndex - fromIndex;
1028             this.modCount = ArrayList.this.modCount;
1029         }
1030 
1031         public E set(int index, E e) {
1032             rangeCheck(index);
1033             checkForComodification();
1034             E oldValue = ArrayList.this.elementData(offset + index);
1035             ArrayList.this.elementData[offset + index] = e;
1036             return oldValue;
1037         }
1038 
1039         public E get(int index) {
1040             rangeCheck(index);
1041             checkForComodification();
1042             return ArrayList.this.elementData(offset + index);
1043         }
1044 
1045         public int size() {
1046             checkForComodification();
1047             return this.size;
1048         }
1049 
1050         public void add(int index, E e) {
1051             rangeCheckForAdd(index);
1052             checkForComodification();
1053             parent.add(parentOffset + index, e);
1054             this.modCount = parent.modCount;
1055             this.size++;
1056         }
1057 
1058         public E remove(int index) {
1059             rangeCheck(index);
1060             checkForComodification();
1061             E result = parent.remove(parentOffset + index);
1062             this.modCount = parent.modCount;
1063             this.size--;
1064             return result;
1065         }
1066 
1067         protected void removeRange(int fromIndex, int toIndex) {
1068             checkForComodification();
1069             parent.removeRange(parentOffset + fromIndex,
1070                                parentOffset + toIndex);
1071             this.modCount = parent.modCount;
1072             this.size -= toIndex - fromIndex;
1073         }
1074 
1075         public boolean addAll(Collection<? extends E> c) {
1076             return addAll(this.size, c);
1077         }
1078 
1079         public boolean addAll(int index, Collection<? extends E> c) {
1080             rangeCheckForAdd(index);
1081             int cSize = c.size();
1082             if (cSize==0)
1083                 return false;
1084 
1085             checkForComodification();
1086             parent.addAll(parentOffset + index, c);
1087             this.modCount = parent.modCount;
1088             this.size += cSize;
1089             return true;
1090         }
1091 
1092         public Iterator<E> iterator() {
1093             return listIterator();
1094         }
1095 
1096         public ListIterator<E> listIterator(final int index) {
1097             checkForComodification();
1098             rangeCheckForAdd(index);
1099             final int offset = this.offset;
1100 
1101             return new ListIterator<E>() {
1102                 int cursor = index;
1103                 int lastRet = -1;
1104                 int expectedModCount = ArrayList.this.modCount;
1105 
1106                 public boolean hasNext() {
1107                     return cursor != SubList.this.size;
1108                 }
1109 
1110                 @SuppressWarnings("unchecked")
1111                 public E next() {
1112                     checkForComodification();
1113                     int i = cursor;
1114                     if (i >= SubList.this.size)
1115                         throw new NoSuchElementException();
1116                     Object[] elementData = ArrayList.this.elementData;
1117                     if (offset + i >= elementData.length)
1118                         throw new ConcurrentModificationException();
1119                     cursor = i + 1;
1120                     return (E) elementData[offset + (lastRet = i)];
1121                 }
1122 
1123                 public boolean hasPrevious() {
1124                     return cursor != 0;
1125                 }
1126 
1127                 @SuppressWarnings("unchecked")
1128                 public E previous() {
1129                     checkForComodification();
1130                     int i = cursor - 1;
1131                     if (i < 0)
1132                         throw new NoSuchElementException();
1133                     Object[] elementData = ArrayList.this.elementData;
1134                     if (offset + i >= elementData.length)
1135                         throw new ConcurrentModificationException();
1136                     cursor = i;
1137                     return (E) elementData[offset + (lastRet = i)];
1138                 }
1139 
1140                 @SuppressWarnings("unchecked")
1141                 public void forEachRemaining(Consumer<? super E> consumer) {
1142                     Objects.requireNonNull(consumer);
1143                     final int size = SubList.this.size;
1144                     int i = cursor;
1145                     if (i >= size) {
1146                         return;
1147                     }
1148                     final Object[] elementData = ArrayList.this.elementData;
1149                     if (offset + i >= elementData.length) {
1150                         throw new ConcurrentModificationException();
1151                     }
1152                     while (i != size && modCount == expectedModCount) {
1153                         consumer.accept((E) elementData[offset + (i++)]);
1154                     }
1155                     // update once at end of iteration to reduce heap write traffic
1156                     lastRet = cursor = i;
1157                     checkForComodification();
1158                 }
1159 
1160                 public int nextIndex() {
1161                     return cursor;
1162                 }
1163 
1164                 public int previousIndex() {
1165                     return cursor - 1;
1166                 }
1167 
1168                 public void remove() {
1169                     if (lastRet < 0)
1170                         throw new IllegalStateException();
1171                     checkForComodification();
1172 
1173                     try {
1174                         SubList.this.remove(lastRet);
1175                         cursor = lastRet;
1176                         lastRet = -1;
1177                         expectedModCount = ArrayList.this.modCount;
1178                     } catch (IndexOutOfBoundsException ex) {
1179                         throw new ConcurrentModificationException();
1180                     }
1181                 }
1182 
1183                 public void set(E e) {
1184                     if (lastRet < 0)
1185                         throw new IllegalStateException();
1186                     checkForComodification();
1187 
1188                     try {
1189                         ArrayList.this.set(offset + lastRet, e);
1190                     } catch (IndexOutOfBoundsException ex) {
1191                         throw new ConcurrentModificationException();
1192                     }
1193                 }
1194 
1195                 public void add(E e) {
1196                     checkForComodification();
1197 
1198                     try {
1199                         int i = cursor;
1200                         SubList.this.add(i, e);
1201                         cursor = i + 1;
1202                         lastRet = -1;
1203                         expectedModCount = ArrayList.this.modCount;
1204                     } catch (IndexOutOfBoundsException ex) {
1205                         throw new ConcurrentModificationException();
1206                     }
1207                 }
1208 
1209                 final void checkForComodification() {
1210                     if (expectedModCount != ArrayList.this.modCount)
1211                         throw new ConcurrentModificationException();
1212                 }
1213             };
1214         }
1215 
1216         public List<E> subList(int fromIndex, int toIndex) {
1217             subListRangeCheck(fromIndex, toIndex, size);
1218             return new SubList(this, offset, fromIndex, toIndex);
1219         }
1220 
1221         private void rangeCheck(int index) {
1222             if (index < 0 || index >= this.size)
1223                 throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
1224         }
1225 
1226         private void rangeCheckForAdd(int index) {
1227             if (index < 0 || index > this.size)
1228                 throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
1229         }
1230 
1231         private String outOfBoundsMsg(int index) {
1232             return "Index: "+index+", Size: "+this.size;
1233         }
1234 
1235         private void checkForComodification() {
1236             if (ArrayList.this.modCount != this.modCount)
1237                 throw new ConcurrentModificationException();
1238         }
1239 
1240         public Spliterator<E> spliterator() {
1241             checkForComodification();
1242             return new ArrayListSpliterator<E>(ArrayList.this, offset,
1243                                                offset + this.size, this.modCount);
1244         }
1245     }
1246 
1247     @Override
1248     public void forEach(Consumer<? super E> action) {
1249         Objects.requireNonNull(action);
1250         final int expectedModCount = modCount;
1251         @SuppressWarnings("unchecked")
1252         final E[] elementData = (E[]) this.elementData;
1253         final int size = this.size;
1254         for (int i=0; modCount == expectedModCount && i < size; i++) {
1255             action.accept(elementData[i]);
1256         }
1257         if (modCount != expectedModCount) {
1258             throw new ConcurrentModificationException();
1259         }
1260     }
1261 
1262     /**
1263      * Creates a <em><a href="Spliterator.html#binding">late-binding</a></em>
1264      * and <em>fail-fast</em> {@link Spliterator} over the elements in this
1265      * list.
1266      *
1267      * <p>The {@code Spliterator} reports {@link Spliterator#SIZED},
1268      * {@link Spliterator#SUBSIZED}, and {@link Spliterator#ORDERED}.
1269      * Overriding implementations should document the reporting of additional
1270      * characteristic values.
1271      *
1272      * @return a {@code Spliterator} over the elements in this list
1273      * @since 1.8
1274      */
1275     @Override
1276     public Spliterator<E> spliterator() {
1277         return new ArrayListSpliterator<>(this, 0, -1, 0);
1278     }
1279 
1280     /** Index-based split-by-two, lazily initialized Spliterator */
1281     static final class ArrayListSpliterator<E> implements Spliterator<E> {
1282 
1283         /*
1284          * If ArrayLists were immutable, or structurally immutable (no
1285          * adds, removes, etc), we could implement their spliterators
1286          * with Arrays.spliterator. Instead we detect as much
1287          * interference during traversal as practical without
1288          * sacrificing much performance. We rely primarily on
1289          * modCounts. These are not guaranteed to detect concurrency
1290          * violations, and are sometimes overly conservative about
1291          * within-thread interference, but detect enough problems to
1292          * be worthwhile in practice. To carry this out, we (1) lazily
1293          * initialize fence and expectedModCount until the latest
1294          * point that we need to commit to the state we are checking
1295          * against; thus improving precision.  (This doesn't apply to
1296          * SubLists, that create spliterators with current non-lazy
1297          * values).  (2) We perform only a single
1298          * ConcurrentModificationException check at the end of forEach
1299          * (the most performance-sensitive method). When using forEach
1300          * (as opposed to iterators), we can normally only detect
1301          * interference after actions, not before. Further
1302          * CME-triggering checks apply to all other possible
1303          * violations of assumptions for example null or too-small
1304          * elementData array given its size(), that could only have
1305          * occurred due to interference.  This allows the inner loop
1306          * of forEach to run without any further checks, and
1307          * simplifies lambda-resolution. While this does entail a
1308          * number of checks, note that in the common case of
1309          * list.stream().forEach(a), no checks or other computation
1310          * occur anywhere other than inside forEach itself.  The other
1311          * less-often-used methods cannot take advantage of most of
1312          * these streamlinings.
1313          */
1314 
1315         private final ArrayList<E> list;
1316         private int index; // current index, modified on advance/split
1317         private int fence; // -1 until used; then one past last index
1318         private int expectedModCount; // initialized when fence set
1319 
1320         /** Create new spliterator covering the given  range */
1321         ArrayListSpliterator(ArrayList<E> list, int origin, int fence,
1322                              int expectedModCount) {
1323             this.list = list; // OK if null unless traversed
1324             this.index = origin;
1325             this.fence = fence;
1326             this.expectedModCount = expectedModCount;
1327         }
1328 
1329         private int getFence() { // initialize fence to size on first use
1330             int hi; // (a specialized variant appears in method forEach)
1331             ArrayList<E> lst;
1332             if ((hi = fence) < 0) {
1333                 if ((lst = list) == null)
1334                     hi = fence = 0;
1335                 else {
1336                     expectedModCount = lst.modCount;
1337                     hi = fence = lst.size;
1338                 }
1339             }
1340             return hi;
1341         }
1342 
1343         public ArrayListSpliterator<E> trySplit() {
1344             int hi = getFence(), lo = index, mid = (lo + hi) >>> 1;
1345             return (lo >= mid) ? null : // divide range in half unless too small
1346                 new ArrayListSpliterator<E>(list, lo, index = mid,
1347                                             expectedModCount);
1348         }
1349 
1350         public boolean tryAdvance(Consumer<? super E> action) {
1351             if (action == null)
1352                 throw new NullPointerException();
1353             int hi = getFence(), i = index;
1354             if (i < hi) {
1355                 index = i + 1;
1356                 @SuppressWarnings("unchecked") E e = (E)list.elementData[i];
1357                 action.accept(e);
1358                 if (list.modCount != expectedModCount)
1359                     throw new ConcurrentModificationException();
1360                 return true;
1361             }
1362             return false;
1363         }
1364 
1365         public void forEachRemaining(Consumer<? super E> action) {
1366             int i, hi, mc; // hoist accesses and checks from loop
1367             ArrayList<E> lst; Object[] a;
1368             if (action == null)
1369                 throw new NullPointerException();
1370             if ((lst = list) != null && (a = lst.elementData) != null) {
1371                 if ((hi = fence) < 0) {
1372                     mc = lst.modCount;
1373                     hi = lst.size;
1374                 }
1375                 else
1376                     mc = expectedModCount;
1377                 if ((i = index) >= 0 && (index = hi) <= a.length) {
1378                     for (; i < hi; ++i) {
1379                         @SuppressWarnings("unchecked") E e = (E) a[i];
1380                         action.accept(e);
1381                     }
1382                     if (lst.modCount == mc)
1383                         return;
1384                 }
1385             }
1386             throw new ConcurrentModificationException();
1387         }
1388 
1389         public long estimateSize() {
1390             return (long) (getFence() - index);
1391         }
1392 
1393         public int characteristics() {
1394             return Spliterator.ORDERED | Spliterator.SIZED | Spliterator.SUBSIZED;
1395         }
1396     }
1397 
1398     @Override
1399     public boolean removeIf(Predicate<? super E> filter) {
1400         Objects.requireNonNull(filter);
1401         // figure out which elements are to be removed
1402         // any exception thrown from the filter predicate at this stage
1403         // will leave the collection unmodified
1404         int removeCount = 0;
1405         final BitSet removeSet = new BitSet(size);
1406         final int expectedModCount = modCount;
1407         final int size = this.size;
1408         for (int i=0; modCount == expectedModCount && i < size; i++) {
1409             @SuppressWarnings("unchecked")
1410             final E element = (E) elementData[i];
1411             if (filter.test(element)) {
1412                 removeSet.set(i);
1413                 removeCount++;
1414             }
1415         }
1416         if (modCount != expectedModCount) {
1417             throw new ConcurrentModificationException();
1418         }
1419 
1420         // shift surviving elements left over the spaces left by removed elements
1421         final boolean anyToRemove = removeCount > 0;
1422         if (anyToRemove) {
1423             final int newSize = size - removeCount;
1424             for (int i=0, j=0; (i < size) && (j < newSize); i++, j++) {
1425                 i = removeSet.nextClearBit(i);
1426                 elementData[j] = elementData[i];
1427             }
1428             for (int k=newSize; k < size; k++) {
1429                 elementData[k] = null;  // Let gc do its work
1430             }
1431             this.size = newSize;
1432             if (modCount != expectedModCount) {
1433                 throw new ConcurrentModificationException();
1434             }
1435             modCount++;
1436         }
1437 
1438         return anyToRemove;
1439     }
1440 
1441     @Override
1442     @SuppressWarnings("unchecked")
1443     public void replaceAll(UnaryOperator<E> operator) {
1444         Objects.requireNonNull(operator);
1445         final int expectedModCount = modCount;
1446         final int size = this.size;
1447         for (int i=0; modCount == expectedModCount && i < size; i++) {
1448             elementData[i] = operator.apply((E) elementData[i]);
1449         }
1450         if (modCount != expectedModCount) {
1451             throw new ConcurrentModificationException();
1452         }
1453         modCount++;
1454     }
1455 
1456     @Override
1457     @SuppressWarnings("unchecked")
1458     public void sort(Comparator<? super E> c) {
1459         final int expectedModCount = modCount;
1460         Arrays.sort((E[]) elementData, 0, size, c);
1461         if (modCount != expectedModCount) {
1462             throw new ConcurrentModificationException();
1463         }
1464         modCount++;
1465     }
1466 }