implements implements と型としてのクラス
最終更新:2026-10-22
implements implements と型としてのクラス
implements はクラスにインターフェースを「請け負わせ」ます。コンパイラは、クラスがインターフェースの要求する全メンバーを提供し、型も一致しているかを項目ごとに検査します。インターフェースが「何ができるか」を述べ、クラスが「どうやるか」に答えます——同じインターフェースに対して、まったく異なる複数の実装が存在できます。
| グループ | 関数とクラス |
|---|---|
| 種類 | 構文 |
| strict モード | 不要 |
ℹ️ 説明 エディタは TypeScript を JavaScript にトランスパイルして実行します(型チェックなし)。型チェック結果は各サンプルの出力を参照してください。
📝 構文
interface Storage {
save(key: string, value: string): void;
load(key: string): string | null;
}
class MemoryStorage implements Storage {
private map = new Map<string, string>();
save(key: string, value: string): void { this.map.set(key, value); }
load(key: string): string | null { return this.map.get(key) ?? null; }
}
⚙️ パラメータ
| implements | インターフェースの宣言:一度に複数を実装できます(implements A, B)。検査の方向は「クラスがインターフェースを満たす」です |
|---|---|
| extends + implements | extends と implements の併用も可能です。class Foo extends Base implements Storage ——実装を継承しながら契約を背負います |
戻り値:メソッドの戻り値型はインターフェースのシグネチャと一致するか、より狭くなければなりません(共変)。パラメータは逆により広く(反変)である必要があり、そうでないとコンパイルエラーになります。
▶ サンプル
下のコードを編集して「試す」を押すと、トランスパイル実行結果を確認できます:
出力:
dark null
(トランスパイル後の実行出力。load メソッドを削除したり戻り値型を string に広げたりするとコンパイルエラーになります——implements は項目ごとに検査します)
💡 ポイント
ℹ️ 説明 implements はコンパイル時の検査であり、実行時の構造には影響しません。トランスパイル後、インターフェースは消え、クラスはただの普通のクラスです。
⚠️ 注意 インターフェースは公開メンバーだけを記述します——private フィールドは implements の検査対象になりません。逆に、インターフェースに書かれたメンバーはクラスに必ず存在しなければならず、1つでも欠けるとエラーです。
💡 ヒント 依存性逆転を実践する手法:業務コードは Storage インターフェースに依存し、テストでは MemoryStorage を、本番では LocalStorage を注入します——呼び出し側のコードは1行も変わりません。
🏷️ 関連関数とクラス
💡 関連ケース
ケースは今後追加予定です。
📚 関連チュートリアル
❓ よくある質問
Q implements と extends の違いは何ですか?
A extends は実装を継承し(コードをもらい)、implements は形状を約束します(契約を背負う)。クラスは1つの親クラスしか extends できませんが、複数のインターフェースを implements できます。
Q implements を書かなくてもクラスをインターフェース型に代入できますか?
A できます——TS は構造的型付けなので、形状が合えば十分です。implements の価値は意図の明示と、「インターフェースが変わったのにクラスが追いついていない」状態をクラス定義の場所でエラーにできることです。代入箇所まで問題を持ち越さずに済みます。
Q インターフェースでコンストラクタの制約を定義できますか?
A できます。new シグネチャを書きます:interface Ctor<T> { new (...args: any[]): T }。ファクトリやコンテナの登録型によく使われます。