Optional Fields
Optional fields (`y?: T`) and destructuring absences are real `T | undefined` values: an omitted field or a pattern position past the source's length reads back as `undefined`, never a stand-in zero. A destructuring default keys off genuine absence — a legitimately stored 0 survives it.
interface User {
name: string;
age?: number;
nickname?: string;
}
const anon: User = { name: "Chrysa" };
const full: User = { name: "Stelios", age: 30, nickname: "stel" };
console.log(anon.age); // undefined
console.log(full.age); // 30
console.log(anon.nickname); // undefined
console.log(anon.age === undefined); // true
console.log(anon.age ?? 18); // 18
console.log(full.age! + 1); // 31
// Writing an optional field makes it present.
anon.age = 44;
console.log(anon.age); // 44
// Destructuring defaults fire on real absence only.
const zero: User = { name: "z", age: 0 };
const { age = 99 } = zero;
console.log(age); // 0 — a stored zero is not "absent"
const m: User = { name: "m" };
const { age: missing = 99 } = m;
console.log(missing); // 99
// Optional class fields work the same way.
class Task {
title: string = "untitled";
deadline?: number;
}
const t = new Task();
console.log(t.deadline); // undefined
// Array destructuring past the source's length binds undefined.
const parts: string[] = ["host"];
const [host, port] = parts;
console.log(host); // host
console.log(port); // undefined
console.log(port ?? "8080"); // 8080
// Enumeration sees only the fields an object has (ADR-01063/ADR-01066):
// an omitted optional field has no key in Object.keys/values/entries,
// for...in, `in`, util.inspect and JSON.stringify.
console.log(Object.keys(anon), Object.values(anon)); // [ 'name', 'age' ] [ 'Chrysa', '44' ]
// (a mixed-type object's values stringify — ADR-00492; a homogeneous one keeps real values)
interface Pt { x: number; y?: number }
const pt: Pt = { x: 1 };
console.log(Object.values(pt), Object.entries(pt)); // [ 1 ] [ [ 'x', 1 ] ]
console.log(Object.entries(m)); // [ [ 'name', 'm' ] ]
for (const k in m) console.log("key", k); // key name
console.log("age" in m, m); // false { name: 'm' }View source on GitHubexamples/objects/optional_fields.ts