Iterating a Map
Fast recall
Quick revision
Core answer
entrySet() or Map.forEach((key, value) -> ...) when you need both key and value, because the entry already carries both. Use keySet() for keys only and values() for values only. Iterating keySet() and then calling get(key) performs an avoidable lookup for every entry; iterating the keys itself is not another hash lookup.Practical Map API knowledge and understanding of performance implications when iterating over key-value pairs
Using keySet plus get when both parts are needed, and incorrectly describing key-set traversal as another hash lookup
Demonstrate knowledge of Map.Entry interface, explain the performance difference between entrySet and keySet iteration, and show the Java 8 map.forEach BiConsumer approach
Interview-ready guide
Interview answer
The best map view depends on which data I need. For both key and value, I normally iterate entrySet() and read entry.getKey() and entry.getValue(), or use map.forEach((key, value) -> ...) for a simple action. The entry already carries both values. Iterating keySet() and then calling get(key) adds an avoidable lookup for every key; iteration of the key set is not itself another hash lookup.
If I need only keys, I use keySet(). If I need only values, I use values(). I choose a normal for-each or explicit iterator when I need to stop early or perform a mutation supported by the view. I also check the concrete map's iteration-order and concurrent-modification rules instead of assuming every Map behaves like HashMap.
Iterating a Map
Direct Answer
Use entrySet() or Map.forEach((key, value) -> ...) when you need both key and value, because the entry already carries both. Use keySet() for keys only and values() for values only. Iterating keySet() and then calling get(key) performs an avoidable lookup for every entry; iterating the keys itself is not another hash lookup.
Code Example
Choose the view that already contains the data the loop needs.
import java.util.*;
public class MapIteration {
public static void main(String[] args) {
Map<Long, String> orders = new HashMap<>();
orders.put(101L, "Laptop");
orders.put(102L, "Mouse");
// Both parts: each entry already contains its key and value.
for (var entry : orders.entrySet()) {
System.out.println(entry.getKey() + " -> " + entry.getValue());
}
// A concise alternative for a simple action.
orders.forEach((id, item) -> System.out.println(id + ": " + item));
// This works, but get(id) is an avoidable lookup when both parts are needed.
for (Long id : orders.keySet()) {
String item = orders.get(id);
System.out.println(id + " => " + item);
}
for (Long id : orders.keySet()) System.out.println(id);
for (String item : orders.values()) System.out.println(item);
}
}
The third loop does one extra lookup per key. It does not perform two hash lookups merely by walking keySet().
Common Mistakes & Pitfalls
- Using
keySet()plusget()for pairs: it works, but eachgetis avoidable whenentrySet()already provides the value. - Calling
entrySet()a hash lookup: it is a live view of the mappings; traversal and key lookup are different operations. - Assuming every map has the same order:
HashMap,LinkedHashMap, andTreeMaphave different iteration rules. - Changing a map without checking its iterator contract: mutation behavior differs across ordinary, unmodifiable, and concurrent maps.
Check your understanding
Answer these without looking back at the article.
- What is Map.Entry?
- Can you remove from a map while iterating with entrySet()?
Looking for a structured roadmap?
Every module on this page is also part of the full Java backend interview track.