TypeScriptにはObjectのもつpropertyに Optional Property という機能があります。
propertyに ? をつけることでそのpropertyがない場合もあるよということを表現することができます。
公式のドキュメントには以下のように記載されています。
- Not all properties of an interface may be required. Some exist under certain conditions or may not be there at all.
ref. https://www.typescriptlang.org/docs/handbook/interfaces.html
あってもなくてもどちらの場合も許容する、propertyを宣言するときに使います。
それだけだと「じゃあそんなpropertyを明示的に宣言する必要があるのか?」とか「正規でpropertyを定義しておけばいいじゃん」となりますが(僕もそう思いました)、例えば以下のような必須でない補足情報を追記したり(case1)、propertyが入ってるケースにおいて型を制限したり(case2)するときに使います。
case1: 何か付加情報を追記したいが、それはoptionalな値であること
interface Person {
name: string // 必須
age: number // 必須
extra?: object // optional
}
case2: propertyが入ってるケースに置いて型を制限する
interface UserAgent {
os?: 'mac' | 'win'
}
このケースでは os propertyは 存在しないかもしれないが、存在する場合は mac or win という文字列のみ許容する という表現になります。
どちらのケースにおいても別に ? をつけなくてもいいと思いますし、つけない方がinterfaceの構造を厳密に定義することができます。
しかし、propertyがないcaseにinterfaceの構造レベルでコンパイルエラーが検出されますし、それだけのためにいらないproperty込でインスタンス化するようなことにもなると思います。
// case1
const person: Person = {name: 'bob', age: 20} //OK
// case1': extra propertyをrequiredにする
const person: Person = {name: 'bob', age: 20} //Error
const person: Person = {name: 'bob', age: 20, extra: {}} //OK
Optional Propertyを使わないケースでのPersonオブジェクトのインスタンス化は冗長です。
また、可読性の観点からも 存在しないかもしれない値だとinterfaceを見ればわかります。
Optional Propertyは Typescriptの表現力の高さを感じさせるものでした。