interfaceとtype
同じ形が 2 通りで書ける
第2章で type を、前回まで interface を使いました。オブジェクトの形を書くだけなら、この 2 つはほぼ同じ結果になります。
interface Work {
readonly id: number;
title: string;
published: boolean;
url?: string;
}
type Work2 = {
readonly id: number;
title: string;
published: boolean;
url?: string;
};type は等号を使い、末尾にセミコロンが要ります。interface は等号を使いません。どちらで書いても、代入できる値は同じです。
増やすときの書き方が違う
差が出るのは、既にある型に項目を足すときです。interface は extends で受け継ぎます。
interface FeaturedWork extends Work {
comment: string;
}type は & でつなぎます。これを交差型と呼びます。
type FeaturedWork = Work & { comment: string };どちらも「Work の全項目 + comment」という同じ形になります。
const pick: FeaturedWork = {
id: 1,
title: "プロフィールサイト",
published: true,
comment: "初めて自分で作ったページです",
};使い分けの基準
迷ったときの目安は次のとおりです。オブジェクトの形に名前を付けるなら interface を選びます。React の props のように、後から誰かが項目を足して広げていく型と相性がよいからです。
一方 type にしかできないことがあります。string | number のような union、タプル、他の型からの計算などです。これらは interface では書けません。
type WorkId = number;
type Status = "draft" | "published";つまり type のほうが守備範囲は広く、interface はオブジェクト専用のかわりに拡張の意図が読み取りやすい、という関係です。同じプロジェクトの中では、どちらを既定にするかを決めて揃えるのがいちばん大事です。
手を動かす
演習では Work を土台にして、おすすめ作品を表す型を作ります。extends と & のどちらで書いても構いません。
要件
FeaturedWorkがWorkのプロパティをすべて受け継ぐようにする- 受け継ぎには
extendsか&を使う。プロパティを手で書き写さない featuredLabelはタイトル - コメントの形で返す
入出力例
featuredLabel({"comment":"初めて自分で作ったページです","id":1,"published":true,"title":"プロフィールサイト"}) → "プロフィールサイト - 初めて自分で作ったページです"
featuredLabel({"comment":"表組みの練習に作りました","id":3,"published":true,"title":"スキル一覧の表","url":"https://example.com/skills"}) → "スキル一覧の表 - 表組みの練習に作りました"
featuredLabel({"comment":"配色を練習中です","id":2,"published":false,"title":"自己紹介カード"}) → "自己紹介カード - 配色を練習中です"ヒント
編集 LuaGate編集部