Java Collections: List, Set, Map and How HashMap Works
Codevity Admin · 10/25/2026
Step 13 of 38 · Java Interview Preparation for Beginners · Stage 3: Collections, generics and exceptions
Codevity Admin · 10/25/2026
The Collections Framework is a guaranteed interview topic, and HashMap is its star question. This article covers the types you must know and the questions that go with them.
| Interface | Meaning | Common implementations |
|---|---|---|
List | Ordered, allows duplicates, index access | ArrayList, LinkedList |
Set | No duplicates | HashSet, LinkedHashSet (insertion order), TreeSet (sorted) |
Map | Key to value, unique keys (not a Collection) | HashMap, LinkedHashMap, TreeMap, ConcurrentHashMap |
Queue / Deque | Ordered for processing at the ends | ArrayDeque, PriorityQueue, LinkedList |
Collection is the interface, and Collections (with an s) is a utility class with helpers such as sort and unmodifiableList.
import java.util.*;
public class Collections101 {
public static void main(String[] args) {
List<String> list = new ArrayList<>(List.of("b", "a", "c", "a"));
Set<String> unique = new LinkedHashSet<>(list);
System.out.println(unique); // [b, a, c]
Map<String, Integer> counts = new HashMap<>();
for (String word : "the cat and the hat".split(" ")) {
counts.merge(word, 1, Integer::sum);
}
System.out.println(new TreeMap<>(counts)); // {and=1, cat=1, hat=1, the=2}
Deque<Integer> stack = new ArrayDeque<>();
stack.push(1);
stack.push(2);
System.out.println(stack.pop()); // 2
Queue<String> queue = new ArrayDeque<>();
queue.offer("first");
queue.offer("second");
System.out.println(queue.poll()); // first
}
}List.of(...), Set.of(...) and Map.of(...) (Java 9) create immutable collections: adding to them throws UnsupportedOperationException.
ArrayList | LinkedList | |
|---|---|---|
| Built on | A resizable array | A doubly linked list of nodes |
get(i) | O(1) | O(n): it walks the nodes |
| Add at the end | Amortized O(1) | O(1) |
| Insert or remove in the middle | O(n): elements shift | O(1) once you are at the node, but finding it is O(n) |
| Memory | Compact | Extra object and two pointers per element |
| Typical use | The default choice | Rarely better. Prefer ArrayDeque for a queue or stack |
ArrayList starts with a default capacity of 10 (allocated on the first add) and grows by about 1.5 times when full.
A HashMap is an array of buckets. Here is what put(key, value) does:
key.hashCode() and spreads the bits so that high bits also matter: hash = h ^ (h >>> 16).index = (capacity - 1) & hash (capacity is always a power of two).equals(): it replaces the value if the key is already there, or appends a new node.Key facts to say aloud:
| Where the order lives | Inside the class () | In a separate object or lambda () |
| How many orders | One natural order | As many as you like |
| Use when | There is one obvious order (numbers, dates, versions) | You sort by different fields, or cannot edit the class |
The iterators of , and most collections are fail-fast: they track a modification count, and if the collection is structurally changed during iteration by anything other than the iterator itself, the next step throws .
To remove safely, use , an explicit and its , or collect the items to delete first. Fail-fast is a best-effort bug detector and not a thread-safety guarantee.
getputnullnullLinkedHashMapTreeMapConcurrentHashMapequals()hashCode()HashSetHashMapComparable<T>Comparator<T>compareTocompareArrayListHashMapConcurrentModificationExceptionremoveIfIteratorremove()HashMap<Character, Integer>HashMaphashCode()index = (n - 1) & (h ^ (h >>> 16)) // simplified from the JDK sourceimport java.util.*;
public class Sorting {
public static void main(String[] args) {
List<Employee> staff = new ArrayList<>(List.of(
new Employee("Asha", "Engineering", 90000),
new Employee("Ben", "Engineering", 75000),
new Employee("Carla", "Sales", 60000),
new Employee("Dev", "Sales", 75000)));
staff.sort(Comparator.comparing(Employee::department)
.thenComparing(Employee::salary, Comparator.reverseOrder()));
for (Employee e : staff) {
System.out.println(e.department() + " " + e.salary() + " " + e.name());
}
// Engineering 90000 Asha, Engineering 75000 Ben, Sales 75000 Dev, Sales 60000 Carla
}
}
record Employee(String name, String department, int salary) {}import java.util.*;
public class FailFast {
public static void main(String[] args) {
List<Integer> numbers = new ArrayList<>(List.of(1, 2, 3, 4));
try {
for (int n : numbers) {
if (n == 2) numbers.remove(Integer.valueOf(n));
}
} catch (ConcurrentModificationException e) {
System.out.println("ConcurrentModificationException"); // ConcurrentModificationException
}
numbers.removeIf(n -> n % 2 == 0);
System.out.println(numbers); // [1, 3]
}
}