JAVA Vector source code parsing and sample code
- 2020-04-01 02:30:08
- OfStack
Vector is introduced in part 1
Vector is a Vector queue, which is a class added in JDK1.0. Subclassed from AbstractList, it implements interfaces like List, RandomAccess, and Cloneable.
Vector implements List by subclassing AbstractList; Therefore, it is a queue that supports the functions of adding, deleting, modifying, traversing and so on.
Vector implements RandmoAccess interface, which provides random access function. RandmoAccess is implemented by List in Java to provide quick access to List. In Vector, we can quickly obtain the element object by the sequence number of the element. This is fast random access.
Vector implements the Cloneable interface, which implements the clone() function. It can be cloned.
Unlike ArrayList, the operations in Vector are thread-safe; However, Vector does not support serialization, that is, the java.io.Serializable interface is not implemented.
The inheritance relationship of Vector
< img SRC = "border = 0 / / files.jb51.net/file_images/article/201311/20131105101519.jpg? 2013105102215 ">
The relationship between Vector and Collection is as follows:
< img SRC = "border = 0 / / files.jb51.net/file_images/article/201311/20131105101530.jpg? 2013105102238 ">
Constructor for Vector
Vector A total of 4 constructors
//Default constructor
Vector()
//Capacity is the default capacity of a Vector. When the capacity is increased due to increased data, the capacity is doubled each time.
Vector(int capacity)
//Capacity is the default size of a Vector, and capacity increment is the increment value each time the Vector's capacity is increased.
Vector(int capacity, int capacityIncrement)
//Create a Vector that contains a collection
Vector(Collection<? extends E> collection)
The Vector of the API
synchronized boolean add(E object)
void add(int location, E object)
synchronized boolean addAll(Collection<? extends E> collection)
synchronized boolean addAll(int location, Collection<? extends E> collection)
synchronized void addElement(E object)
synchronized int capacity()
void clear()
synchronized Object clone()
boolean contains(Object object)
synchronized boolean containsAll(Collection<?> collection)
synchronized void copyInto(Object[] elements)
synchronized E elementAt(int location)
Enumeration<E> elements()
synchronized void ensureCapacity(int minimumCapacity)
synchronized boolean equals(Object object)
synchronized E firstElement()
E get(int location)
synchronized int hashCode()
synchronized int indexOf(Object object, int location)
int indexOf(Object object)
synchronized void insertElementAt(E object, int location)
synchronized boolean isEmpty()
synchronized E lastElement()
synchronized int lastIndexOf(Object object, int location)
synchronized int lastIndexOf(Object object)
synchronized E remove(int location)
boolean remove(Object object)
synchronized boolean removeAll(Collection<?> collection)
synchronized void removeAllElements()
synchronized boolean removeElement(Object object)
synchronized void removeElementAt(int location)
synchronized boolean retainAll(Collection<?> collection)
synchronized E set(int location, E object)
synchronized void setElementAt(E object, int location)
synchronized void setSize(int length)
synchronized int size()
synchronized List<E> subList(int start, int end)
synchronized <T> T[] toArray(T[] contents)
synchronized Object[] toArray()
synchronized String toString()
synchronized void trimToSize()
Part 2 Vector source code analysis
In order to understand the principle of Vector, the following Vector source code is analyzed.
package java.util;
public class Vector<E>
extends AbstractList<E>
implements List<E>, RandomAccess, Cloneable, java.io.Serializable
{
//An array that holds the data in a Vector
protected Object[] elementData;
//The amount of actual data
protected int elementCount;
//Capacity growth coefficient
protected int capacityIncrement;
//The sequence version number of Vector
private static final long serialVersionUID = -2767605614048989439L;
//Vector constructor. The default capacity is 10.
public Vector() {
this(10);
}
//Specifies the constructor for the size of the Vector
public Vector(int initialCapacity) {
this(initialCapacity, 0);
}
//Specifies the constructor for the "capacity size" and "growth factor" of the Vector
public Vector(int initialCapacity, int capacityIncrement) {
super();
if (initialCapacity < 0)
throw new IllegalArgumentException("Illegal Capacity: "+
initialCapacity);
//Create a new array with initialCapacity
this.elementData = new Object[initialCapacity];
//Set the capacity growth factor
this.capacityIncrement = capacityIncrement;
}
//Specifies the Vector constructor for the collection.
public Vector(Collection<? extends E> c) {
//Gets the array of collection (c) and assigns it to elementData
elementData = c.toArray();
//Set array length
elementCount = elementData.length;
// c.toArray might (incorrectly) not return Object[] (see 6260652)
if (elementData.getClass() != Object[].class)
elementData = Arrays.copyOf(elementData, elementCount, Object[].class);
}
//Copy all the elements of the array Vector into the array anArray
public synchronized void copyInto(Object[] anArray) {
System.arraycopy(elementData, 0, anArray, 0, elementCount);
}
//Set the current capacity value to = the actual number of elements
public synchronized void trimToSize() {
modCount++;
int oldCapacity = elementData.length;
if (elementCount < oldCapacity) {
elementData = Arrays.copyOf(elementData, elementCount);
}
}
//Verify the help function for "Vector capacity"
private void ensureCapacityHelper(int minCapacity) {
int oldCapacity = elementData.length;
//When the capacity of the Vector is insufficient to hold all the current elements, increase the capacity.
//If capacity increment coefficient> 0 (namely capacityIncrement> 0), then increment the capacity as increment
//Otherwise, double the volume.
if (minCapacity > oldCapacity) {
Object[] oldData = elementData;
int newCapacity = (capacityIncrement > 0) ?
(oldCapacity + capacityIncrement) : (oldCapacity * 2);
if (newCapacity < minCapacity) {
newCapacity = minCapacity;
}
elementData = Arrays.copyOf(elementData, newCapacity);
}
}
//Determine the capacity of the Vector.
public synchronized void ensureCapacity(int minCapacity) {
//Change the Vector by +1
modCount++;
ensureCapacityHelper(minCapacity);
}
//Set the capacity value to newSize
public synchronized void setSize(int newSize) {
modCount++;
if (newSize > elementCount) {
//If "newSize is greater than Vector capacity ", resize the Vector.
ensureCapacityHelper(newSize);
} else {
//If "newSize is less than/equal to Vector capacity ", set all elements starting at the newSize position to null
for (int i = newSize ; i < elementCount ; i++) {
elementData[i] = null;
}
}
elementCount = newSize;
}
//Return "total capacity of Vector"
public synchronized int capacity() {
return elementData.length;
}
//Returns the "actual size of the Vector", that is, the number of elements in the Vector
public synchronized int size() {
return elementCount;
}
//Determine whether the Vector is empty
public synchronized boolean isEmpty() {
return elementCount == 0;
}
//Returns "Enumeration for all elements in a Vector"
public Enumeration<E> elements() {
//Implement an Enumeration through an anonymous class
return new Enumeration<E>() {
int count = 0;
//Does the next element exist
public boolean hasMoreElements() {
return count < elementCount;
}
//Gets the next element
public E nextElement() {
synchronized (Vector.this) {
if (count < elementCount) {
return (E)elementData[count++];
}
}
throw new NoSuchElementException("Vector Enumeration");
}
};
}
//Returns whether the Vector contains an object (o)
public boolean contains(Object o) {
return indexOf(o, 0) >= 0;
}
//Start at the index position and look backward for the element (o).
//If found, returns the index value of the element; Otherwise, it returns negative 1
public synchronized int indexOf(Object o, int index) {
if (o == null) {
//If the element is found to be null, the null element is found forward and its corresponding sequence number is returned
for (int i = index ; i < elementCount ; i++)
if (elementData[i]==null)
return i;
} else {
//If the element is not null, the element is found forward and its corresponding sequence number is returned
for (int i = index ; i < elementCount ; i++)
if (o.equals(elementData[i]))
return i;
}
return -1;
}
//Finds and returns the index value of the element (o) in the Vector
public int indexOf(Object o) {
return indexOf(o, 0);
}
//Look for the element (o) backwards. And returns the index of the element
public synchronized int lastIndexOf(Object o) {
return lastIndexOf(o, elementCount-1);
}
//Look for the element (o) backwards. The starting position is the index number from front to back;
//If found, returns the "index value" of the element; Otherwise, it returns negative 1.
public synchronized int lastIndexOf(Object o, int index) {
if (index >= elementCount)
throw new IndexOutOfBoundsException(index + " >= "+ elementCount);
if (o == null) {
//If the element is found to be null, the null element is found in reverse and its corresponding sequence number is returned
for (int i = index; i >= 0; i--)
if (elementData[i]==null)
return i;
} else {
//If the element is not null, the element is reversed and its corresponding sequence number is returned
for (int i = index; i >= 0; i--)
if (o.equals(elementData[i]))
return i;
}
return -1;
}
//Returns an element at the index position in a Vector.
//If index monthly statement, an exception is thrown
public synchronized E elementAt(int index) {
if (index >= elementCount) {
throw new ArrayIndexOutOfBoundsException(index + " >= " + elementCount);
}
return (E)elementData[index];
}
//Gets the first element in the Vector.
//If it fails, an exception is thrown!
public synchronized E firstElement() {
if (elementCount == 0) {
throw new NoSuchElementException();
}
return (E)elementData[0];
}
//Gets the last element in the Vector.
//If it fails, an exception is thrown!
public synchronized E lastElement() {
if (elementCount == 0) {
throw new NoSuchElementException();
}
return (E)elementData[elementCount - 1];
}
//Set the value of the element at the index position to obj
public synchronized void setElementAt(E obj, int index) {
if (index >= elementCount) {
throw new ArrayIndexOutOfBoundsException(index + " >= " +
elementCount);
}
elementData[index] = obj;
}
//Delete the element at the index position
public synchronized void removeElementAt(int index) {
modCount++;
if (index >= elementCount) {
throw new ArrayIndexOutOfBoundsException(index + " >= " +
elementCount);
} else if (index < 0) {
throw new ArrayIndexOutOfBoundsException(index);
}
int j = elementCount - index - 1;
if (j > 0) {
System.arraycopy(elementData, index + 1, elementData, index, j);
}
elementCount--;
elementData[elementCount] = null;
}
//Insert element (obj) at index
public synchronized void insertElementAt(E obj, int index) {
modCount++;
if (index > elementCount) {
throw new ArrayIndexOutOfBoundsException(index
+ " > " + elementCount);
}
ensureCapacityHelper(elementCount + 1);
System.arraycopy(elementData, index, elementData, index + 1, elementCount - index);
elementData[index] = obj;
elementCount++;
}
//Add "element obj" to the end of the Vector
public synchronized void addElement(E obj) {
modCount++;
ensureCapacityHelper(elementCount + 1);
elementData[elementCount++] = obj;
}
//Find and delete the element obj in the Vector.
//Returns true on success; Otherwise, false is returned.
public synchronized boolean removeElement(Object obj) {
modCount++;
int i = indexOf(obj);
if (i >= 0) {
removeElementAt(i);
return true;
}
return false;
}
//Delete all elements in the Vector
public synchronized void removeAllElements() {
modCount++;
//Set all elements in the Vector to null
for (int i = 0; i < elementCount; i++)
elementData[i] = null;
elementCount = 0;
}
//Cloning function
public synchronized Object clone() {
try {
Vector<E> v = (Vector<E>) super.clone();
//Copies all the elements of the current Vector into v
v.elementData = Arrays.copyOf(elementData, elementCount);
v.modCount = 0;
return v;
} catch (CloneNotSupportedException e) {
// this shouldn't happen, since we are Cloneable
throw new InternalError();
}
}
//Returns an array of objects
public synchronized Object[] toArray() {
return Arrays.copyOf(elementData, elementCount);
}
//Returns an array of templates for the Vector. Called a template array, that is, you can set T to any data type
public synchronized <T> T[] toArray(T[] a) {
//If the size of array a <The number of elements of Vector;
//Then create a new T[] array with the size of "the number of elements of Vector" and copy all "Vector" into the new array
if (a.length < elementCount)
return (T[]) Arrays.copyOf(elementData, elementCount, a.getClass());
//If the size of array a> = the number of elements of Vector;
//Then copy all the elements of the Vector into array a.
System.arraycopy(elementData, 0, a, 0, elementCount);
if (a.length > elementCount)
a[elementCount] = null;
return a;
}
//Gets the element of the index position
public synchronized E get(int index) {
if (index >= elementCount)
throw new ArrayIndexOutOfBoundsException(index);
return (E)elementData[index];
}
//Set the value of the index position to element. And returns the original value of the index position
public synchronized E set(int index, E element) {
if (index >= elementCount)
throw new ArrayIndexOutOfBoundsException(index);
Object oldValue = elementData[index];
elementData[index] = element;
return (E)oldValue;
}
//Add "element e" to the end of the Vector.
public synchronized boolean add(E e) {
modCount++;
ensureCapacityHelper(elementCount + 1);
elementData[elementCount++] = e;
return true;
}
//Delete the element o in the Vector
public boolean remove(Object o) {
return removeElement(o);
}
//Add the element element at the index position
public void add(int index, E element) {
insertElementAt(element, index);
}
//Delete the element at the index position And return index The original value of the position
public synchronized E remove(int index) {
modCount++;
if (index >= elementCount)
throw new ArrayIndexOutOfBoundsException(index);
Object 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 work
return (E)oldValue;
}
//Empty Vector
public void clear() {
removeAllElements();
}
//Returns whether the Vector contains the set c
public synchronized boolean containsAll(Collection<?> c) {
return super.containsAll(c);
}
//Add the collection cto the Vector
public synchronized boolean addAll(Collection<? extends E> c) {
modCount++;
Object[] a = c.toArray();
int numNew = a.length;
ensureCapacityHelper(elementCount + numNew);
//Copy all the elements of collection c into the array elementData
System.arraycopy(a, 0, elementData, elementCount, numNew);
elementCount += numNew;
return numNew != 0;
}
//Delete all elements of collection c
public synchronized boolean removeAll(Collection<?> c) {
return super.removeAll(c);
}
//Delete "elements in non-set c"
public synchronized boolean retainAll(Collection<?> c) {
return super.retainAll(c);
}
//Starting at the index position, add the collection cto the Vector
public synchronized boolean addAll(int index, Collection<? extends E> c) {
modCount++;
if (index < 0 || index > elementCount)
throw new ArrayIndexOutOfBoundsException(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;
}
//Returns whether two objects are equal
public synchronized boolean equals(Object o) {
return super.equals(o);
}
//Calculate the hash value
public synchronized int hashCode() {
return super.hashCode();
}
//Call parent toString()
public synchronized String toString() {
return super.toString();
}
//Gets a subset of fromIndex(including) to toIndex(excluding) in the Vector
public synchronized List<E> subList(int fromIndex, int toIndex) {
return Collections.synchronizedList(super.subList(fromIndex, toIndex), this);
}
//Delete fromIndex to toIndex elements in Vector
protected synchronized void removeRange(int fromIndex, int toIndex) {
modCount++;
int numMoved = elementCount - toIndex;
System.arraycopy(elementData, toIndex, elementData, fromIndex,
numMoved);
// Let gc do its work
int newElementCount = elementCount - (toIndex-fromIndex);
while (elementCount != newElementCount)
elementData[--elementCount] = null;
}
//Write to java.io.Serializable
private synchronized void writeObject(java.io.ObjectOutputStream s)
throws java.io.IOException {
s.defaultWriteObject();
}
}
Conclusion:
(01) Vector actually stores data through an array. When we construct Vecotr; If the default constructor is used, the default capacity of the Vector is 10.
(02) when the Vector capacity is insufficient to contain all elements, the capacity of the Vector will increase. If capacity increase coefficient > 0, then increase the value of capacity by "capacity increase coefficient"; Otherwise, double the volume.
(03) the cloning function of Vector is to clone all the elements into an array.
Part 3 the Vector traversal method
Vector supports four traversal modes. It is recommended to use the second option below to traverse the Vector due to efficiency issues.
(01) The first is traversal through an iterator. through Iterator To traverse.
Integer value = null;
int size = vec.size();
for (int i=0; i<size; i++) {
value = (Integer)vec.get(i);
}
(02) The second, random access, is traversed by index values.
Due to the Vector To achieve the RandomAccess Interface, which supports random access to elements by index values.
Integer value = null;
int size = vec.size();
for (int i=0; i<size; i++) {
value = (Integer)vec.get(i);
}
(03) The third, the other for Cycle. As follows:
Integer value = null;
for (Integer integ:vec) {
value = integ;
}
(04) The fourth, Enumeration Traverse. As follows:
Integer value = null;
Enumeration enu = vec.elements();
while (enu.hasMoreElements()) {
value = (Integer)enu.nextElement();
}
The code to test the efficiency of these traversal methods is as follows:
import java.util.*;
public class VectorRandomAccessTest {
public static void main(String[] args) {
Vector vec= new Vector();
for (int i=0; i<100000; i++)
vec.add(i);
iteratorThroughRandomAccess(vec) ;
iteratorThroughIterator(vec) ;
iteratorThroughFor2(vec) ;
iteratorThroughEnumeration(vec) ;
}
private static void isRandomAccessSupported(List list) {
if (list instanceof RandomAccess) {
System.out.println("RandomAccess implemented!");
} else {
System.out.println("RandomAccess not implemented!");
}
}
public static void iteratorThroughRandomAccess(List list) {
long startTime;
long endTime;
startTime = System.currentTimeMillis();
for (int i=0; i<list.size(); i++) {
list.get(i);
}
endTime = System.currentTimeMillis();
long interval = endTime - startTime;
System.out.println("iteratorThroughRandomAccess : " + interval+" ms");
}
public static void iteratorThroughIterator(List list) {
long startTime;
long endTime;
startTime = System.currentTimeMillis();
for(Iterator iter = list.iterator(); iter.hasNext(); ) {
iter.next();
}
endTime = System.currentTimeMillis();
long interval = endTime - startTime;
System.out.println("iteratorThroughIterator : " + interval+" ms");
}
public static void iteratorThroughFor2(List list) {
long startTime;
long endTime;
startTime = System.currentTimeMillis();
for(Object obj:list)
endTime = System.currentTimeMillis();
long interval = endTime - startTime;
System.out.println("iteratorThroughFor2 : " + interval+" ms");
}
public static void iteratorThroughEnumeration(Vector vec) {
long startTime;
long endTime;
startTime = System.currentTimeMillis();
for(Enumeration enu = vec.elements(); enu.hasMoreElements(); ) {
enu.nextElement();
}
endTime = System.currentTimeMillis();
long interval = endTime - startTime;
System.out.println("iteratorThroughEnumeration : " + interval+" ms");
}
}
Operation results:
IteratorThroughRandomAccess: 6 ms
9 iteratorThroughIterator: ms
IteratorThroughFor2:8 ms
IteratorThroughEnumeration: 7 ms
Summary: through the Vector, the random access method using the index is the fastest and the iterator is the slowest.
Part 4 Vector example
Let's learn how to use a Vector through an example
import java.util.Vector;
import java.util.List;
import java.util.Iterator;
import java.util.Enumeration;
public class VectorTest {
public static void main(String[] args) {
//A new Vector
Vector vec = new Vector();
//Add elements
vec.add("1");
vec.add("2");
vec.add("3");
vec.add("4");
vec.add("5");
//Set the first element to 100
vec.set(0, "100");
//Insert "500" into the third position
vec.add(2, "300");
System.out.println("vec:"+vec);
//Gets the index of 100
System.out.println("vec.indexOf(100):"+vec.indexOf("100"));
//Gets the index of 100
System.out.println("vec.lastIndexOf(100):"+vec.lastIndexOf("100"));
//Gets the first element
System.out.println("vec.firstElement():"+vec.firstElement());
//Gets the third element
System.out.println("vec.elementAt(2):"+vec.elementAt(2));
//Gets the last element
System.out.println("vec.lastElement():"+vec.lastElement());
//Gets the size of the Vector
System.out.println("size:"+vec.size());
//Gets the total capacity of the Vector
System.out.println("capacity:"+vec.capacity());
//Gets the "2nd" to "4th" elements of the vector
System.out.println("vec 2 to 4:"+vec.subList(1, 4));
//The Vector is traversed by an Enumeration
Enumeration enu = vec.elements();
while(enu.hasMoreElements())
System.out.println("nextElement():"+enu.nextElement());
Vector retainVec = new Vector();
retainVec.add("100");
retainVec.add("300");
//Gets the collection of elements in the "vec" contained in the "retainVec"
System.out.println("vec.retain():"+vec.retainAll(retainVec));
System.out.println("vec:"+vec);
//Gets the String array corresponding to the vec
String[] arr = (String[]) vec.toArray(new String[0]);
for (String str:arr)
System.out.println("str:"+str);
//Empty Vector. Clear () is the same as removeAllElements()!
vec.clear();
// vec.removeAllElements();
//Determine whether the Vector is empty
System.out.println("vec.isEmpty():"+vec.isEmpty());
}
}