package java.util;import java.io.IOException;import java.io.ObjectInputStream;import java.io.StreamCorruptedException;import java.util.function.Consumer;import java.util.function.Predicate;import java.util.function.UnaryOperator;publicclassVector<E>extendsAbstractList<E>implementsList<E>, RandomAccess, Cloneable, java.io.Serializable
{/*
* Vector的分量存储在其中的数组缓冲区。Vector的容量是这个数组缓冲区的长度,并且至少大到可以包含向量的所有元素。
*/protected Object[] elementData;/*
* 这个向量对象中有效分量的数量。
*/protectedint elementCount;/*
* 当向量的大小大于其容量时,其容量自动递增的量。如果容量增量小于或等于零,则每次需要增长时,向量的容量将增加一倍。
*/protectedint capacityIncrement;/** use serialVersionUID from JDK 1.0.2 for interoperability */privatestaticfinallong serialVersionUID =-2767605614048989439L;/*
* 构造具有指定初始容量和容量增量的空Vector。
*/publicVector(int initialCapacity,int capacityIncrement){super();if(initialCapacity <0)thrownewIllegalArgumentException("Illegal Capacity: "+ initialCapacity);this.elementData =newObject[initialCapacity];this.capacityIncrement = capacityIncrement;}publicVector(int initialCapacity){this(initialCapacity,0);}publicVector(){this(10);}/*
* 构造一个Vector,其中包含指定集合的元素,按集合的迭代器返回元素的顺序排列。
*/publicVector(Collection<?extendsE> c){
elementData = c.toArray();
elementCount = elementData.length;// c.toArray might (incorrectly) not return Object[] (see 6260652)if(elementData.getClass()!= Object[].class)
elementData = Arrays.copyOf(elementData, elementCount, Object[].class);}/*
* 将此Vector的组件复制到指定的数组中。这个Vector中下标k的项被复制到anArray的分量k中。
*/publicsynchronizedvoidcopyInto(Object[] anArray){
System.arraycopy(elementData,0, anArray,0, elementCount);}/*
* 将该Vector的容量修剪为该Vector的当前大小。如果该Vector的容量大于其当前大小,
* 则通过将其保存在字段elementData中的内部数据数组替换为一个更小的数组,将容量更改为等于大小。应用程序可以使用此操作最小化向量的存储。
*/publicsynchronizedvoidtrimToSize(){
modCount++;int oldCapacity = elementData.length;if(elementCount < oldCapacity){
elementData = Arrays.copyOf(elementData, elementCount);}}/*
* 如果需要,增加这个Vector的容量,以确保它至少可以容纳由最小容量参数指定的组件数量。
* 如果该Vector的当前容量小于minCapacity,则通过替换字段elementData中的内部数据数组来增加其容量。
* 新数据数组的大小将是旧的大小加上扩充容量,除非扩充容量的值小于或等于零,在这种情况下,新容量将是旧容量的两倍;
* 但如果新容量仍然小于minCapacity,那么新容量将是minCapacity。【和ArrayList处理基本相同不多解释】
*/publicsynchronizedvoidensureCapacity(int minCapacity){if(minCapacity >0){
modCount++;ensureCapacityHelper(minCapacity);}}privatevoidensureCapacityHelper(int minCapacity){// overflow-conscious codeif(minCapacity - elementData.length >0)grow(minCapacity);}privatestaticfinalint MAX_ARRAY_SIZE = Integer.MAX_VALUE -8;privatevoidgrow(int minCapacity){// overflow-conscious codeint 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);}privatestaticinthugeCapacity(int minCapacity){if(minCapacity <0)// overflowthrownewOutOfMemoryError();return(minCapacity > MAX_ARRAY_SIZE)? Integer.MAX_VALUE : MAX_ARRAY_SIZE;}/*
* 设置这个Vector的大小。如果新大小大于当前大小,则在向量的末尾添加新的空项。如果新大小小于当前大小,
* 则索引为newSize之后的所有组件都将被丢弃。
*/publicsynchronizedvoidsetSize(int newSize){
modCount++;if(newSize > elementCount){ensureCapacityHelper(newSize);}else{for(int i = newSize; i < elementCount; i++){
elementData[i]= null;}}
elementCount = newSize;}/**
* 返回此向量的当前容量。
*/publicsynchronizedintcapacity(){return elementData.length;}/*
* 返回这个向量的组件数。
*/publicsynchronizedintsize(){return elementCount;}publicsynchronizedbooleanisEmpty(){return elementCount ==0;}/*
* 返回此Vector的组件的枚举。返回的枚举对象将生成此Vector中的所有项。生成的第一个项是索引0处的项,然后是索引1处的项,依此类推。
*/public Enumeration<E>elements(){returnnewEnumeration<E>(){int count =0;publicbooleanhasMoreElements(){return count < elementCount;}public E nextElement(){synchronized(Vector.this){if(count < elementCount){returnelementData(count++);}}thrownewNoSuchElementException("Vector Enumeration");}};}/*
* 如果该向量包含指定的元素,则返回true。
*/publicbooleancontains(Object o){returnindexOf(o,0)>=0;}/*
* 返回该向量中指定元素第一次出现的索引,如果该向量不包含该元素,则返回-1。
*/publicintindexOf(Object o){returnindexOf(o,0);}/*
* 返回该向量中指定元素第一次出现时的索引,从索引中向前搜索;如果没有找到该元素,则返回-1。
*/publicsynchronizedintindexOf(Object o,int index){if(o == null){for(int i = index; i < elementCount; i++)if(elementData[i]== null)return i;}else{for(int i = index; i < elementCount; i++)if(o.equals(elementData[i]))return i;}return-1;}/*
* 逆向遍历 返回该向量中指定元素第一次出现的索引,如果该向量不包含该元素,则返回-1。
*/publicsynchronizedintlastIndexOf(Object o){returnlastIndexOf(o, elementCount -1);}publicsynchronizedintlastIndexOf(Object o,int index){if(index >= elementCount)thrownewIndexOutOfBoundsException(index +" >= "+ elementCount);if(o == null){for(int i = index; i >=0; i--)if(elementData[i]== null)return i;}else{for(int i = index; i >=0; i--)if(o.equals(elementData[i]))return i;}return-1;}/*
* 返回指定索引处的组件。 此方法在功能上与get(int)方法相同(后者是List接口的一部分)。
*/publicsynchronized E elementAt(int index){if(index >= elementCount){thrownewArrayIndexOutOfBoundsException(index +" >= "+ elementCount);}returnelementData(index);}/*
* 返回此向量的第一个组件(索引为0的项)。
*/publicsynchronized E firstElement(){if(elementCount ==0){thrownewNoSuchElementException();}returnelementData(0);}/**
* Returns the last component of the vector.
*/publicsynchronized E lastElement(){if(elementCount ==0){thrownewNoSuchElementException();}returnelementData(elementCount -1);}/*
* 将此向量的指定索引处的组件设置为指定对象。该位置上的前一个组件被丢弃。 索引的值必须大于或等于0,并且小于向量的当前大小。
* 此方法在功能上与set(int,
* E)方法(它是List接口的一部分)相同。注意,set方法颠倒了参数的顺序,以便更接近数组的用法。还要注意,set方法返回存储在指定位置的旧值。
*/publicsynchronizedvoidsetElementAt(E obj,int index){if(index >= elementCount){thrownewArrayIndexOutOfBoundsException(index +" >= "+ elementCount);}
elementData[index]= obj;}/*
* 删除指定索引处的组件。这个向量中索引大于或等于指定索引的每个分量向下移动,使索引比先前的值小一个。这个向量的大小减少了1。
* 索引的值必须大于或等于0,并且小于向量的当前大小。
* 该方法在功能上与remove(int)方法相同(后者是List接口的一部分)。注意,remove方法返回存储在指定位置的旧值。
*/publicsynchronizedvoidremoveElementAt(int index){
modCount++;if(index >= elementCount){thrownewArrayIndexOutOfBoundsException(index +" >= "+ elementCount);}elseif(index <0){thrownewArrayIndexOutOfBoundsException(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 */}/*
* 在指定索引处将指定对象作为此Vector中的组件插入。这个Vector中索引大于或等于指定索引的每个分量向上移动,使索引大于先前的值。
* 索引的值必须大于或等于0,并且小于或等于向量的当前大小。(如果索引等于向量的当前大小,则将新元素追加到Vector。)此方法在功能上与add(
* int, E)方法(列表接口的一部分)相同。注意,add方法颠倒了参数的顺序,以便更接近于匹配数组的使用。
* 【这里就很有意思了,对小于elementCount并没有进行判断,以前的方法是判断的了的,即使不判断System.
* arraycopy也能对负数index抛出正确的异常,因此判断不判断也显得不那么重要了】
*/publicsynchronizedvoidinsertElementAt(E obj,int index){
modCount++;if(index > elementCount){thrownewArrayIndexOutOfBoundsException(index +" > "+ elementCount);}ensureCapacityHelper(elementCount +1);
System.arraycopy(elementData, index, elementData, index +1, elementCount - index);
elementData[index]= obj;
elementCount++;}/*
* 将指定的组件添加到该Vector的末尾,将其大小增加1。如果Vector的大小大于其容量,则该向量的容量将增加。
* 此方法在功能上与add(E)方法(列表接口的一部分)相同。
*/publicsynchronizedvoidaddElement(E obj){
modCount++;ensureCapacityHelper(elementCount +1);
elementData[elementCount++]= obj;}publicsynchronizedbooleanremoveElement(Object obj){
modCount++;int i =indexOf(obj);if(i >=0){removeElementAt(i);returntrue;}returnfalse;}publicsynchronizedvoidremoveAllElements(){
modCount++;// Let gc do its workfor(int i =0; i < elementCount; i++)
elementData[i]= null;
elementCount =0;}/*
* 返回此向量的克隆。副本将包含对内部数据数组的克隆的引用,而不是对这个向量对象的原始内部数据数组的引用。
*/publicsynchronized Object clone(){try{@SuppressWarnings("unchecked")
Vector<E> v =(Vector<E>)super.clone();
v.elementData = Arrays.copyOf(elementData, elementCount);
v.modCount =0;return v;}catch(CloneNotSupportedException e){// this shouldn't happen, since we are CloneablethrownewInternalError(e);}}/*
* 返回一个数组,该数组以正确的顺序包含这个Vector中的所有元素。
*/publicsynchronized Object[]toArray(){return Arrays.copyOf(elementData, elementCount);}/*
* 返回一个数组,其中包含该Vector中所有元素的正确顺序;返回数组的运行时类型是指定数组的运行时类型。如果Vector符合指定的数组,
* 则返回该Vector。否则, 将使用指定数组的运行时类型和该向量的大小分配新数组。
* 如果向量符合指定的数组,则有剩余空间(即,数组的元素数多于向量),数组中紧接向量末尾的元素被设为null。(只有在调用方知道向量不包含任何空元素时
* ,这在确定向量长度时才有用。) 【当a.length <
* elementCount,直接按elementData值和size转数组,否则按a.length创建新数组,
* 前几位存elementData值之后存a的值,最后将elementData长度的那一位置null做标志位】
*/@SuppressWarnings("unchecked")publicsynchronized<T> T[]toArray(T[] a){if(a.length < elementCount)return(T[])Arrays.copyOf(elementData, elementCount, a.getClass());
System.arraycopy(elementData,0, a,0, elementCount);if(a.length > elementCount)
a[elementCount]= null;return a;}// Positional Access Operations@SuppressWarnings("unchecked")
E elementData(int index){return(E)elementData[index];}/*
* 返回该向量中指定位置的元素。
*/publicsynchronized E get(int index){if(index >= elementCount)thrownewArrayIndexOutOfBoundsException(index);returnelementData(index);}publicsynchronized E set(int index, E element){if(index >= elementCount)thrownewArrayIndexOutOfBoundsException(index);
E oldValue =elementData(index);
elementData[index]= element;return oldValue;}publicsynchronizedbooleanadd(E e){
modCount++;ensureCapacityHelper(elementCount +1);
elementData[elementCount++]= e;returntrue;}publicbooleanremove(Object o){returnremoveElement(o);}publicvoidadd(int index, E element){insertElementAt(element, index);}publicsynchronized E remove(int index){
modCount++;if(index >= elementCount)thrownewArrayIndexOutOfBoundsException(index);
E oldValue =elementData(index);int numMoved = elementCount - index -1;if(numMoved >0)
System.arraycopy(elementData, index +1, elementData, index, numMoved);
elementData[--elementCount]= null;// Let gc do its workreturn oldValue;}publicvoidclear(){removeAllElements();}publicsynchronizedbooleancontainsAll(Collection<?> c){returnsuper.containsAll(c);}publicsynchronizedbooleanaddAll(Collection<?extendsE> c){
modCount++;
Object[] a = c.toArray();int numNew = a.length;ensureCapacityHelper(elementCount + numNew);
System.arraycopy(a,0, elementData, elementCount, numNew);
elementCount += numNew;return numNew !=0;}publicsynchronizedbooleanremoveAll(Collection<?> c){returnsuper.removeAll(c);}publicsynchronizedbooleanretainAll(Collection<?> c){returnsuper.retainAll(c);}publicsynchronizedbooleanaddAll(int index, Collection<?extendsE> c){
modCount++;if(index <0|| index > elementCount)thrownewArrayIndexOutOfBoundsException(index);
Object[] a = c.toArray();int numNew = a.length;ensureCapacityHelper(elementCount + numNew);int numMoved = elementCount - index;if(numMoved >0)
System.arraycopy(elementData, index, elementData, index + numNew, numMoved);
System.arraycopy(a,0, elementData, index, numNew);
elementCount += numNew;return numNew !=0;}/*
* 父类的equals方法写的很棒,先和自己比较确定是否是引用,在确定对象是否是list,在比较每个元素是否都为null,都不是null再比较是否相等
* ,最后确定两个都是否遍历完
*/publicsynchronizedbooleanequals(Object o){returnsuper.equals(o);}publicsynchronizedinthashCode(){returnsuper.hashCode();}publicsynchronized String toString(){returnsuper.toString();}/**
* Returns a view of the portion of this List between fromIndex, inclusive,
* and toIndex, exclusive. (If fromIndex and toIndex are equal, the returned
* List is empty.) The returned List is backed by this List, so changes in
* the returned List are reflected in this List, and vice-versa. The
* returned List supports all of the optional List operations supported by
* this List.
* <p>
* This method eliminates the need for explicit range operations (of the
* sort that commonly exist for arrays). Any operation that expects a List
* can be used as a range operation by operating on a subList view instead
* of a whole List. For example, the following idiom removes a range of
* elements from a List: <pre>
* list.subList(from, to).clear();
* </pre> Similar idioms may be constructed for indexOf and lastIndexOf, and
* all of the algorithms in the Collections class can be applied to a
* subList.
* <p>
* The semantics of the List returned by this method become undefined if the
* backing list (i.e., this List) is <i>structurally modified</i> in any way
* other than via the returned List. (Structural modifications are those
* that change the size of the List, or otherwise perturb it in such a
* fashion that iterations in progress may yield incorrect results.)
*
* @param fromIndex low endpoint (inclusive) of the subList
* @param toIndex high endpoint (exclusive) of the subList
* @return a view of the specified range within this List
* @throws IndexOutOfBoundsException if an endpoint index value is out of
* range {@code (fromIndex < 0 || toIndex > size)}
* @throws IllegalArgumentException if the endpoint indices are out of order
* {@code (fromIndex > toIndex)}
*/publicsynchronized List<E>subList(int fromIndex,int toIndex){return Collections.synchronizedList(super.subList(fromIndex, toIndex),this);}/**
* Removes from this list all of the elements whose index is between
* {@code fromIndex}, inclusive, and {@code toIndex}, exclusive. Shifts any
* succeeding elements to the left (reduces their index). This call shortens
* the list by {@code (toIndex - fromIndex)} elements. (If
* {@code toIndex==fromIndex}, this operation has no effect.)
*/protectedsynchronizedvoidremoveRange(int fromIndex,int toIndex){
modCount++;int numMoved = elementCount - toIndex;
System.arraycopy(elementData, toIndex, elementData, fromIndex, numMoved);// Let gc do its workint newElementCount = elementCount -(toIndex - fromIndex);while(elementCount != newElementCount)
elementData[--elementCount]= null;}/**
* Loads a {@code Vector} instance from a stream (that is, deserializes it).
* This method performs checks to ensure the consistency of the fields.
*
* @param in the stream
* @throws java.io.IOException if an I/O error occurs
* @throws ClassNotFoundException if the stream contains data of a
* non-existing class
*/privatevoidreadObject(ObjectInputStream in)throws IOException, ClassNotFoundException
{
ObjectInputStream.GetField gfields = in.readFields();int count = gfields.get("elementCount",0);
Object[] data =(Object[])gfields.get("elementData", null);if(count <0|| data == null || count > data.length){thrownewStreamCorruptedException("Inconsistent vector internals");}
elementCount = count;
elementData = data.clone();}/**
* Save the state of the {@code Vector} instance to a stream (that is,
* serialize it). This method performs synchronization to ensure the
* consistency of the serialized data.
*/privatevoidwriteObject(java.io.ObjectOutputStream s)throws java.io.IOException
{final java.io.ObjectOutputStream.PutField fields = s.putFields();final Object[] data;synchronized(this){
fields.put("capacityIncrement", capacityIncrement);
fields.put("elementCount", elementCount);
data = elementData.clone();}
fields.put("elementData", data);
s.writeFields();}/**
* Returns a list iterator over the elements in this list (in proper
* sequence), starting at the specified position in the list. The specified
* index indicates the first element that would be returned by an initial
* call to {@link ListIterator#next next}. An initial call to
* {@link ListIterator#previous previous} would return the element with the
* specified index minus one.
* <p>
* The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
*
* @throws IndexOutOfBoundsException {@inheritDoc}
*/publicsynchronized ListIterator<E>listIterator(int index){if(index <0|| index > elementCount)thrownewIndexOutOfBoundsException("Index: "+ index);returnnewListItr(index);}/**
* Returns a list iterator over the elements in this list (in proper
* sequence).
* <p>
* The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
*
* @see #listIterator(int)
*/publicsynchronized ListIterator<E>listIterator(){returnnewListItr(0);}/**
* Returns an iterator over the elements in this list in proper sequence.
* <p>
* The returned iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
*
* @return an iterator over the elements in this list in proper sequence
*/publicsynchronized Iterator<E>iterator(){returnnewItr();}/**
* An optimized version of AbstractList.Itr
*/privateclassItrimplementsIterator<E>{int cursor;// index of next element to returnint lastRet =-1;// index of last element returned; -1 if no suchint expectedModCount = modCount;publicbooleanhasNext(){// Racy but within spec, since modifications are checked// within or after synchronization in next/previousreturn cursor != elementCount;}public E next(){synchronized(Vector.this){checkForComodification();int i = cursor;if(i >= elementCount)thrownewNoSuchElementException();
cursor = i +1;returnelementData(lastRet = i);}}publicvoidremove(){if(lastRet ==-1)thrownewIllegalStateException();synchronized(Vector.this){checkForComodification();
Vector.this.remove(lastRet);
expectedModCount = modCount;}
cursor = lastRet;
lastRet =-1;}@OverridepublicvoidforEachRemaining(Consumer<?super E> action){
Objects.requireNonNull(action);synchronized(Vector.this){finalint size = elementCount;int i = cursor;if(i >= size){return;}@SuppressWarnings("unchecked")final E[] elementData =(E[])Vector.this.elementData;if(i >= elementData.length){thrownewConcurrentModificationException();}while(i != size && modCount == expectedModCount){
action.accept(elementData[i++]);}// update once at end of iteration to reduce heap write traffic
cursor = i;
lastRet = i -1;checkForComodification();}}finalvoidcheckForComodification(){if(modCount != expectedModCount)thrownewConcurrentModificationException();}}/**
* An optimized version of AbstractList.ListItr
*/finalclassListItrextendsItrimplementsListIterator<E>{ListItr(int index){super();
cursor = index;}publicbooleanhasPrevious(){return cursor !=0;}publicintnextIndex(){return cursor;}publicintpreviousIndex(){return cursor -1;}public E previous(){synchronized(Vector.this){checkForComodification();int i = cursor -1;if(i <0)thrownewNoSuchElementException();
cursor = i;returnelementData(lastRet = i);}}publicvoidset(E e){if(lastRet ==-1)thrownewIllegalStateException();synchronized(Vector.this){checkForComodification();
Vector.this.set(lastRet, e);}}publicvoidadd(E e){int i = cursor;synchronized(Vector.this){checkForComodification();
Vector.this.add(i, e);
expectedModCount = modCount;}
cursor = i +1;
lastRet =-1;}}@OverridepublicsynchronizedvoidforEach(Consumer<?super E> action){
Objects.requireNonNull(action);finalint expectedModCount = modCount;@SuppressWarnings("unchecked")final E[] elementData =(E[])this.elementData;finalint elementCount =this.elementCount;for(int i =0; modCount == expectedModCount && i < elementCount; i++){
action.accept(elementData[i]);}if(modCount != expectedModCount){thrownewConcurrentModificationException();}}@Override@SuppressWarnings("unchecked")publicsynchronizedbooleanremoveIf(Predicate<?super E> filter){
Objects.requireNonNull(filter);// figure out which elements are to be removed// any exception thrown from the filter predicate at this stage// will leave the collection unmodifiedint removeCount =0;finalint size = elementCount;final BitSet removeSet =newBitSet(size);finalint expectedModCount = modCount;for(int i =0; modCount == expectedModCount && i < size; i++){@SuppressWarnings("unchecked")final E element =(E)elementData[i];if(filter.test(element)){
removeSet.set(i);
removeCount++;}}if(modCount != expectedModCount){thrownewConcurrentModificationException();}// shift surviving elements left over the spaces left by removed// elementsfinalboolean anyToRemove = removeCount >0;if(anyToRemove){finalint newSize = size - removeCount;for(int i =0, j =0;(i < size)&&(j < newSize); i++, j++){
i = removeSet.nextClearBit(i);
elementData[j]= elementData[i];}for(int k = newSize; k < size; k++){
elementData[k]= null;// Let gc do its work}
elementCount = newSize;if(modCount != expectedModCount){thrownewConcurrentModificationException();}
modCount++;}return anyToRemove;}@Override@SuppressWarnings("unchecked")publicsynchronizedvoidreplaceAll(UnaryOperator<E> operator){
Objects.requireNonNull(operator);finalint expectedModCount = modCount;finalint size = elementCount;for(int i =0; modCount == expectedModCount && i < size; i++){
elementData[i]= operator.apply((E)elementData[i]);}if(modCount != expectedModCount){thrownewConcurrentModificationException();}
modCount++;}@SuppressWarnings("unchecked")@Overridepublicsynchronizedvoidsort(Comparator<?super E> c){finalint expectedModCount = modCount;
Arrays.sort((E[])elementData,0, elementCount, c);if(modCount != expectedModCount){thrownewConcurrentModificationException();}
modCount++;}/**
* Creates a <em><a href="Spliterator.html#binding">late-binding</a></em>
* and <em>fail-fast</em> {@link Spliterator} over the elements in this
* list.
* <p>
* The {@code Spliterator} reports {@link Spliterator#SIZED},
* {@link Spliterator#SUBSIZED}, and {@link Spliterator#ORDERED}. Overriding
* implementations should document the reporting of additional
* characteristic values.
*
* @return a {@code Spliterator} over the elements in this list
* @since 1.8
*/@Overridepublic Spliterator<E>spliterator(){returnnewVectorSpliterator<>(this, null,0,-1,0);}/** Similar to ArrayList Spliterator */staticfinalclassVectorSpliterator<E>implementsSpliterator<E>{privatefinal Vector<E> list;private Object[] array;privateint index;// current index, modified on advance/splitprivateint fence;// -1 until used; then one past last indexprivateint expectedModCount;// initialized when fence set/** Create new spliterator covering the given range */VectorSpliterator(Vector<E> list, Object[] array,int origin,int fence,int expectedModCount){this.list = list;this.array = array;this.index = origin;this.fence = fence;this.expectedModCount = expectedModCount;}privateintgetFence(){// initialize on first useint hi;if((hi = fence)<0){synchronized(list){
array = list.elementData;
expectedModCount = list.modCount;
hi = fence = list.elementCount;}}return hi;}public Spliterator<E>trySplit(){int hi =getFence(), lo = index, mid =(lo + hi)>>>1;return(lo >= mid)? null :newVectorSpliterator<E>(list, array, lo, index = mid, expectedModCount);}@SuppressWarnings("unchecked")publicbooleantryAdvance(Consumer<?super E> action){int i;if(action == null)thrownewNullPointerException();if(getFence()>(i = index)){
index = i +1;
action.accept((E)array[i]);if(list.modCount != expectedModCount)thrownewConcurrentModificationException();returntrue;}returnfalse;}@SuppressWarnings("unchecked")publicvoidforEachRemaining(Consumer<?super E> action){int i, hi;// hoist accesses and checks from loop
Vector<E> lst;
Object[] a;if(action == null)thrownewNullPointerException();if((lst = list)!= null){if((hi = fence)<0){synchronized(lst){
expectedModCount = lst.modCount;
a = array = lst.elementData;
hi = fence = lst.elementCount;}}else
a = array;if(a != null &&(i = index)>=0&&(index = hi)<= a.length){while(i < hi)
action.accept((E)a[i++]);if(lst.modCount == expectedModCount)return;}}thrownewConcurrentModificationException();}publiclongestimateSize(){return(long)(getFence()- index);}publicintcharacteristics(){return Spliterator.ORDERED | Spliterator.SIZED | Spliterator.SUBSIZED;}}}