Question 8
What does this print?
```java
import java.util.*;
public class Main {
record Coord(int x, int y) {}
public static void main(String[] args) {
Set<Coord> seen = new HashSet<>();
seen.add(new Coord(1, 2));
seen.add(new Coord(1, 2));
Map<Coord, String> map = new HashMap<>();
map.put(new Coord(3, 4), "hi");
System.out.print(seen.size() + " " + map.get(new Coord(3, 4)));
}
}
```
A. Compilation fails: a record must override hashCode to be used as a hash key
Invents a rule; overriding hashCode in a record is permitted but never required, and nothing about HashMap demands it.
B. 2 null
The answer you get if you believe records inherit Object's identity-based equals/hashCode like a plain class — the classic hand-written-key bug; records generate value-based equals/hashCode, so they are the fix for exactly that.
C. 1 null
Assumes equals is generated (so the set dedupes) but that a HashMap lookup still needs the identical key object; the generated hashCode is derived from the same components as equals, so a fresh Coord(3, 4) lands in the same bucket and finds the stored value.
D. 1 hiCorrect answer
A record derives equals and hashCode from all of its components, so two separately built Coord(1, 2) are equal and hash alike — HashSet rejects the duplicate (size 1) and a fresh Coord(3, 4) retrieves the stored value, giving `1 hi`.
Explanation
Trace: a record automatically gets `equals` and `hashCode` derived from all of its components, so two separately constructed `Coord(1, 2)` instances are equal *and* hash alike. `HashSet` therefore rejects the second `add` as a duplicate and `seen.size()` is `1`. For the same reason a freshly built `new Coord(3, 4)` lands in the same bucket as the key that was stored and compares equal to it, so `map.get(...)` returns `"hi"`. The output is `1 hi`.
Why the others are wrong:
`2 null` is the answer you get if you believe records inherit `Object`'s identity-based `equals`/`hashCode` like a plain class with no overrides — the classic reason a hand-written key class fails. Records are the fix for exactly that bug.
`1 null` splits the difference: it assumes `equals` is generated (so the set dedupes) but that a `HashMap` lookup still needs the identical key object. Any lookup that finds nothing does so because the *hash* disagrees, and the generated `hashCode` is derived from the same components as `equals`, so the two can never disagree here.
`Compilation fails: a record must override hashCode to be used as a hash key` invents a rule. Overriding `hashCode` in a record is permitted but never required, and nothing about `HashMap` demands it.
Exam tip: records are correct-by-construction hash keys — value equality over every component, with a `hashCode` consistent with it. The trap is a record with an array component: array `equals` is identity, so `record Data(int[] vals)` breaks the contract and two `Data` holding `{1, 2, 3}` are *not* equal.