Return after two or three days. Try these challenges without reading old solutions first. Retrieval after a delay helps reveal which ideas you can use independently. Spend about twenty minutes, then revisit the relevant lesson for any gap.
Challenge 1 — lookup: implement a generic first helper for a readonly list. It must preserve the element type and allow an empty list. Demonstrate a safe caller for both strings and numbers.
Challenge 2 — boundary: write a guard for a finite nonnegative integer from unknown. Include zero, NaN, Infinity, negative numbers and numeric text in your tests. Explain why typeof alone is insufficient.
Challenge 3 — update: write a helper that appends a topic to a readonly string list by creating a new list. Show that the original is unchanged. Explain why readonly is not Object.freeze.
Finally, explain three distinctions in plain language: checking versus execution; a type assertion versus runtime validation; and a clean compiler result versus evidence that the program implements its intended behavior. If you can only repeat definitions, find a concrete example from your own exercise.
The example below deliberately contains a logic mistake that passes checking. The optional diagnostic lab contains a type mistake. Compare the evidence needed to find each.
Predict, check, then run
Before running, write down the output and explain which information the checker knows. Click Check types first, then Check & run.
function remaining(pages: number, read: number): number {
return pages + read;
}
console.log(remaining(100, 40));Enable JavaScript to edit and type-check this example.
Check your prediction
140 Read a real compiler error
Identify the unsafe assumption before checking. Then explain why a runtime test and a type check give different evidence from the arithmetic example above.
const first: string | undefined = undefined;
console.log(first.toUpperCase());Enable JavaScript to edit and type-check this example.
Check your diagnosis
The first value may be absent. Add a real branch or optional chaining with an intentional fallback. Do not append ! to make the diagnostic disappear.
Your turn
Come Back Later: Review Challenges: practise
Complete the three review challenges above. Print TYPES for the first string, 0 for a missing first number using a fallback, true for a valid zero, false for numeric text, Types for the original list and Types,Review for the copied list.
// Attempt all three helpers from memory. Keep unknown data guarded.Enable JavaScript to edit and type-check this example.
Hint 1: the idea
Use a type parameter for the relationship, conditions for evidence, and a copy for the update.
Hint 2: a first step
First write each function’s input and return annotation; then implement the JavaScript operation.
Show one solution
function first<T>(items: readonly T[]): T | undefined {
return items[0];
}
function isCount(value: unknown): value is number {
return (
typeof value === "number" &&
Number.isFinite(value) &&
Number.isInteger(value) &&
value >= 0
);
}
function addTopic(topics: readonly string[], topic: string): string[] {
return [...topics, topic];
}
console.log(first(["Types"])?.toUpperCase() ?? "Empty");
console.log(first<number>([]) ?? 0);
console.log(isCount(0));
console.log(isCount("0"));
const original = ["Types"];
console.log(original.join(","));
console.log(addTopic(original, "Review").join(","));Enable JavaScript to edit and type-check this example.
TYPES
0
true
false
Types
Types,ReviewExplain the types at the function boundary and the runtime checks, if any. Compare your approach before copying this answer.
Change it and explain it
Fix remaining to subtract and write a regression assertion. If any challenge required the solution, retry it next week with a different domain. Continue with intermediate JavaScript for modules and asynchronous applications; advanced JavaScript and further TypeScript levels can build on this foundation later.
Completion is saved in this browser only. It does not measure mastery.