Practice Solutions and Feedback
Attempt first; alternative designs are valid when they preserve the stated observations and explain their costs.
P01: Freeze the boundary
The public trace includes header, rows, clock and total. Private helper names are excluded; rounding and clock timing are included. State supported inputs before claiming equivalence.
P02: Characterize rounding
Each row rounds to 34 cents. Sum 68; at time 9 the discounted total rounds to 61; at 10 and 11 it stays 68. Aggregate rounding would produce 67 before discount.
P03: Preserve a failure trace
The header is written first; the row is consumed; source failure propagates. No clock or total write occurs. Buffering before the header intentionally changes this behavior.
P04: Specify a clock seam
A changing environment during row iteration distinguishes early acquisition from a late callable. Preserve one clock read after successful input consumption.
P05: Challenge the oracle
Changing < to <= gives the discount at equality. Differential agreement can preserve a shared bug; separate specification oracles and approved repairs.
P06: Extract without changing traversal
Pass the current row to a helper that validates and returns its rounded amount. Do not move validation before the header or convert the iterator twice.
P07: Inline an effectful argument
Evaluate nextValue once into a fresh local and multiply that value by itself. Check order, scope and exceptions as well as arithmetic.
P08: Rename a published API
Keep a delegating alias until supported callers and the compatibility policy allow retirement. A repository search cannot establish that external jobs have migrated.
P09: Split phase with error order
Keep quantity as text until after SKU lookup. X fails with KeyError first; eager int conversion would expose ValueError instead.
P10: Inspect value-wrapper compatibility
Check JSON serialization, key enumeration, prototype/identity, mutations through aliases and public type. Accessors alone do not preserve them.
P11: Consolidate lazily
A lazy generator with any preserves first-truthy stopping. Eager lists evaluate untaken branches, including failures or writes.
P12: Choose a dispatch boundary
Closed matching or an external operation may localize new operations; a hierarchy can favor adding variants. Recurrence alone does not decide.
P13: Specify a parameter object
Choose explicit inclusive/exclusive endpoints and immutable values or ownership rules. New rejection of invalid dates or reversed ranges is a contract change unless already enforced.
P14: Move with a facade
Retain a delegating export and test old and new entry points. Remove only under an established compatibility policy; a stable facade may remain permanently.
P15: Budget a refactor
Use concrete change pressure and costs. Dedicated migration work can be justified; neither three duplicates nor a line count mandates a refactor.
P16: Exercise mixed clients
Both interfaces observe one authority. Empty string is a stored value, None means absent. Invalid calls preserve existing state; separate all-old/all-new tests are insufficient.
P17: Trace acknowledgement loss
The effect may have committed. A second provider can duplicate it. Propagate uncertainty; reconciliation and durable deduplication require additional contracts.
P18: Plan state migration
The in-memory lab does not solve these. Define authority, version compatibility, checkpointed backfill, reconciliation and recovery before switching stateful clients.
P19: Design rollback and retirement
Routing back changes traffic only. Old code must understand current data; irreversible effects may need reconciliation or compensation. Retirement needs evidence, owner and a deadline or deliberate retention decision.
P20: Separate a repair
The two 335-thousandth rows change 68 to 67 at equality. That is a policy repair/change, not preservation. Keep the original baseline and label the new contract.