導入
T のままだと「何でも入る」ので、.length のような特定のプロパティを使う処理は書けません。extends で「T はこの形を満たすものに限る」という制約をかけられます。また、型引数は1つに限らず複数使えます。
説明
<T extends { length: number }> と書くと、「length プロパティを持つ型」だけを受け付けるようになります。
function printLength<T extends { length: number }>(x: T): void {
console.log(x.length);
}
printLength("hello"); // string には length がある
printLength([1, 2, 3]); // 配列にも length がある
// printLength(42); // エラー: number には length がないので渡せない
型引数はカンマで区切って複数使えます。キーと値のペアのような、2種類の型を扱う関数でよく使います。
function pair<K, V>(key: K, value: V): [K, V] {
return [key, value];
}
console.log(pair("age", 25));
やってみよう
printLength(42) のコメントアウトを外して実行し、number には .length がないことをコードから確認してみましょう(このランナーは型チェックまでは行わないため、実際に手元の VS Code など型チェックのある環境で試すとエラー表示が見られます)。
演習
function makeMap<K, V>(key: K, value: V): { key: K; value: V } という、キーと値を1つのオブジェクトにまとめる関数を作ってください。console.log(makeMap("id", 1).value) で結果を表示してください。
ヒント1を見る
function makeMap<K, V>(key: K, value: V): { key: K; value: V } { return { key, value }; }
ヒント2を見る
console.log(makeMap("id", 1).value);