⚡ Play a quiz
HomeLearnLanguagesJava › Collections framework
Lesson 2 of 2 · Java

Java Collections Framework: Choosing the Right Structure

Java100%

"Which collection would you use?" is a design question wearing a syntax costume. The interviewer wants to hear the access pattern drive the choice — and to hear you name the cost you are accepting in exchange.

Read time
9 min
Track
Languages
Sections
4
Practice
4

List: ArrayList or LinkedList

The two List implementations
OperationArrayListLinkedList
get(i)O(1)O(n)
add() at the endO(1) amortisedO(1)
add(0, x)O(n)O(1)
remove(i)O(n)O(n) to find, O(1) to unlink
Memory per elementOne slotSlot plus two pointers plus node header
tip

The honest answer is almost always ArrayList

LinkedList wins on paper for front insertion, and loses in practice almost everywhere else: contiguous memory means an ArrayList scan is far friendlier to the CPU cache, and shifting elements is a single fast block move. Use ArrayDeque, not LinkedList, when you genuinely need cheap operations at both ends.

ArrayList — one contiguous block 42 17 99 8 one cache line brings in the neighbours too get(i): O(1) add(0,x): O(n) LinkedList — a node per element, wherever memory was free 42 17 99 8 get(i): O(n) add(0,x): O(1) + 2 pointers per element
Both scans are O(n), but only one of them is cache-friendly — which is why ArrayList wins in practice almost everywhere.

Map: Hash, Linked or Tree

Choosing a Map
ImplementationOrderGet / putUse when
HashMapNoneO(1) averageThe default — you only need lookup
LinkedHashMapInsertion orderO(1) averageOrder must be stable, or building an LRU cache
TreeMapSorted by keyO(log n)You need sorted iteration or range queries
ConcurrentHashMapNoneO(1) averageMultiple threads write to it

TreeMap earns its extra log factor with methods a hash map cannot offer: firstKey(), floorKey(), headMap(), subMap(). If a problem asks for "the largest key not exceeding x", that is a TreeMap signal.

Common mistake

Reaching for Hashtable or Collections.synchronizedMap

Both lock the entire map for every operation, so threads queue behind each other. ConcurrentHashMap locks per bucket and scales far better — it is the correct answer for a shared mutable map.

Sets and queues

  • HashSet — O(1) membership, no order. The default set.
  • LinkedHashSet — O(1) membership, insertion order preserved. Useful for deduplicating while keeping order.
  • TreeSet — O(log n), sorted, with first(), ceiling() and range views.
  • ArrayDeque — O(1) at both ends; the right choice for a stack or a queue.
  • PriorityQueue — a binary heap; O(log n) insert and remove, O(1) peek at the smallest. The top-k workhorse.
warn

Stack and Vector are legacy

Both synchronise every method for a threading model Java left behind, and Stack even iterates bottom-up, which surprises everyone. Use ArrayDeque for a stack and ArrayList for a list.

The gotchas interviewers ask about

Common mistake

ConcurrentModificationException

Removing from a collection while iterating it with a for-each loop throws at the next step. Use Iterator.remove(), or removeIf(), or iterate over a copy.

Removing safely
// Throws ConcurrentModificationException
for (String s : list) {
    if (s.isEmpty()) list.remove(s);
}

// Correct, and clearer
list.removeIf(String::isEmpty);
Common mistake

Arrays.asList() is fixed size

It returns a view backed by the array, so add() and remove() throw UnsupportedOperationException. Wrap it — new ArrayList<>(Arrays.asList(...)) — when you need a mutable list.

One more, worth saying before you are asked: any object used as a HashMap key or in a HashSet must implement equals() and hashCode() consistently, and must not be mutated afterwards.

Key takeaways

  • ArrayList is the default List; LinkedList rarely wins outside a whiteboard.
  • HashMap by default, LinkedHashMap for order, TreeMap for sorted and range queries.
  • ConcurrentHashMap for shared mutable maps; Hashtable and synchronizedMap lock everything.
  • Use removeIf or Iterator.remove — never remove inside a for-each loop.

Practice

ProblemPatternLevel
Build an LRU cache with LinkedHashMapAccess-order mapMedium
Find the top k frequent elementsHashMap + PriorityQueueMedium
Deduplicate a list while preserving orderLinkedHashSetEasy
Implement a stack using ArrayDequeDeque as stackEasy

Frequently asked questions

What is the difference between ArrayList and LinkedList?

ArrayList is backed by a resizable array: O(1) indexed access, O(n) insertion at the front, and excellent cache behaviour. LinkedList is a doubly linked list: O(1) insertion at the ends, O(n) access by index, and more memory per element.

When should I use a TreeMap instead of a HashMap?

When you need keys in sorted order, or range operations such as floorKey, headMap and subMap. You pay O(log n) per operation instead of O(1) average for that capability.

What causes a ConcurrentModificationException?

Structurally modifying a collection while iterating it with a for-each loop. The iterator detects the modification count changed and fails fast. Use Iterator.remove() or removeIf() instead.

Test yourself on Java

Reading is not recall. Take a timed quiz on this topic solo, or share a room code and battle friends on it.

⚡ Start the Java quiz

More in Java