Enums — Practice Tasks¶
Twelve exercises in enum design, strategy enums, EnumSet/EnumMap, and pattern matching.
Task 1 — Days of the week¶
Define enum Day { MONDAY, ..., SUNDAY } with: - boolean isWeekend() returning true for SAT/SUN - int hoursOfDaylight(Month m) (mock implementation) - A static EnumSet<Day> WEEKEND = EnumSet.of(SATURDAY, SUNDAY);
Task 2 — Strategy enum¶
Define enum Op with PLUS, MINUS, TIMES, DIVIDE. Each has an abstract int apply(int a, int b). Implement per-constant. Test:
Task 3 — Enum + interface¶
Define interface Operation { int apply(int a, int b); } and enum BasicOp implements Operation. Show that you can pass either a BasicOp constant or a custom lambda to a method expecting Operation.
Task 4 — Enum singleton¶
Implement a Database singleton via enum: - Hold a fake Connection field - Provide save(Object) and query(String) methods - Verify the same instance via Database.INSTANCE == Database.INSTANCE
Task 5 — Per-constant data¶
Define enum HttpStatus with constants and per-constant code and description fields. Add static factory from(int code) returning the corresponding constant or null.
Task 6 — EnumSet vs HashSet benchmark¶
Create a JMH benchmark comparing: - EnumSet.of(...) vs Set.of(...) for contains operations - EnumMap vs HashMap for get operations
Verify EnumSet/EnumMap are faster.
Task 7 — State machine with enum¶
Model a vending machine:
Each state implementson(Event e) returning the next state. Task 8 — Switch with binding¶
Pattern-match a enum Op in a switch (Java 21+) with: - Guard: case PLUS when isCommutative() - Constants combined: case PLUS, MINUS -> "binary"
Task 9 — Enum from JSON¶
Using Jackson, serialize an enum Color { RED, GREEN, BLUE } as JSON. Test: - Default: "RED" - Custom via @JsonValue to lowercase: "red"
Task 10 — Don't store ordinal¶
Given an existing system that stores direction.ordinal() in DB: 1. Reorder constants and observe corruption 2. Refactor to store name() 3. Discuss migration path
Task 11 — Enum implementing Comparator¶
Define enum SortBy with BY_NAME, BY_AGE, BY_DATE — each implements Comparator<User>. Use users.sort(SortBy.BY_AGE).
Task 12 — Migrate enum to sealed records¶
Given:
Refactor to:
sealed interface Shape { ... }
record Circle(double radius) implements Shape { ... }
record Square(double side) implements Shape { ... }
record Triangle(double base, double h) implements Shape { ... }
Compare: how does the data model change? When is each preferable?
Validation¶
| Task | How |
|---|---|
| 1 | Day.SATURDAY.isWeekend() is true |
| 2 | Op.PLUS.apply(3, 4) == 7 |
| 3 | Can pass both BasicOp.PLUS and (a, b) -> a*b |
| 4 | Database.INSTANCE == Database.INSTANCE is true; reflection throws |
| 5 | HttpStatus.from(404).description() returns Not Found |
| 6 | JMH shows EnumSet/EnumMap faster |
| 7 | Verify state transitions match expected sequence |
| 8 | Switch compiles with guard; covers all cases |
| 9 | JSON output matches expected format |
| 10 | After reorder, ordinal-based DB has wrong directions |
| 11 | Sort produces correct order |
| 12 | Records carry per-variant data; sealed gives exhaustive matching |
Memorize this: enums are for closed sets of labels with optional per-constant behavior. Use EnumSet/EnumMap for performance. Use enum + interface for SPI. Use sealed records when variants carry typed data. Don't use ordinal() for persistence.