Introduction
A Vector in Java is a part of the java.util package and is used to store a dynamic array similar to ArrayList. However, Vector is synchronized, making it thread-safe but slower in comparison to ArrayList.
1. Data Structure Used
Vector is implemented using a dynamic array, meaning it grows automatically when more elements are added.
Implementation in Java:
public class Vector<E> extends AbstractList<E> {
protected Object[] elementData;
protected int elementCount;
protected int capacityIncrement;
}
- The
elementDataarray holds the actual elements. - The
elementCountkeeps track of the current number of elements. - The
capacityIncrementdetermines how much the array should grow when resized.
2. How Elements are Stored and Accessed
Adding an Element
When add() is called:
- If there is space, the element is added at
elementData[elementCount], andelementCountis incremented. - If the array is full, it expands (either doubles in size or increases by
capacityIncrement).
Example:
Vector<String> vector = new Vector<>();
vector.add("Apple");
vector.add("Banana");
vector.add("Cherry");
System.out.println(vector); // Output: [Apple, Banana, Cherry]
Retrieving an Element
Elements are accessed using the get() method, which uses direct indexing (O(1)):
System.out.println(vector.get(1)); // Output: Banana
Removing an Element
When remove(index) is called:
- The element at the given index is removed.
- All subsequent elements are shifted left by one position.
elementCountis decremented.
Example:
vector.remove(1); // Removes "Banana" System.out.println(vector); // Output: [Apple, Cherry]
3. Resizing Mechanism
How Vector Expands
- When a
Vectorexceeds its capacity, it creates a new array. - The new size is double the old size (default behavior) or increases by
capacityIncrementif specified. - All elements from the old array are copied into the new array.
Example:
Vector<Integer> numbers = new Vector<>(2); numbers.add(1); numbers.add(2); numbers.add(3); // Triggers resizing System.out.println(numbers); // Output: [1, 2, 3]
4. Synchronization and Performance
Unlike ArrayList, Vector is synchronized, making it thread-safe but slower in performance.
Thread-Safety Mechanism
All methods in Vector are synchronized to prevent concurrent modifications:
public synchronized boolean add(E e) {
modCount++;
ensureCapacityHelper(elementCount + 1);
elementData[elementCount++] = e;
return true;
}
However, if synchronization is not required, using an ArrayList with manual synchronization is recommended for better performance:
List<String> list = Collections.synchronizedList(new ArrayList<>());
5. Performance Analysis
| Operation | Time Complexity |
|---|---|
| Add at End | O(1) (Amortized) |
| Add at Index | O(n) (Shifting required) |
| Get Element | O(1) (Direct Access) |
| Remove Element | O(n) (Shifting required) |
Comparison with ArrayList
| Feature | Vector (Synchronized) | ArrayList (Not Synchronized) |
|---|---|---|
| Access by Index | ✅ Fast (O(1)) | ✅ Fast (O(1)) |
| Insert at End | ✅ Fast (O(1)) | ✅ Fast (O(1)) |
| Insert at Beginning | ❌ Slow (O(n)) | ❌ Slow (O(n)) |
| Thread-Safe | ✅ Yes | ❌ No (Must be manually synchronized) |
6. Key Takeaways
✔ Vector is thread-safe due to synchronization but has lower performance than ArrayList.
✔ Expands dynamically when full, doubling its capacity by default.
✔ Adding/removing at the end is fast (O(1)), but inserting/removing in the middle requires shifting (O(n)).
✔ Use Vector only when thread safety is required; otherwise, ArrayList is preferred for better performance.
Understanding the internal working of Vector helps optimize Java applications and choose the right data structure for multi-threaded environments.