メインコンテンツまでスキップ

状態遷移ロジックの集中

説明(どんな問題か)

どんな状態か?

  • オブジェクトが持つ状態に応じて処理を変えたいが、状態と振る舞いが密結合
  • ifswitch 文で状態ごとの処理を管理している
  • 状態が増えると処理が肥大化し、読みにくくなる

なぜ問題か?

  • 状態が増えるたびに、既存コードを修正する必要がある(開閉原則違反
  • 責務が 1 クラスに集中して、テスト困難・可読性低下
  • 将来的な拡張や状態遷移ロジックが煩雑になる

アンチパターンのコード例

class Document {
private state: string = "draft"; // 状態: 'draft', 'review', 'published'

publish() {
if (this.state === "draft") {
console.log("レビュー依頼を送信");
this.state = "review";
} else if (this.state === "review") {
console.log("公開しました");
this.state = "published";
} else if (this.state === "published") {
console.log("すでに公開済みです");
}
}
}

問題点:

  • 状態が文字列で管理され、振る舞いも 1 クラスに集中
  • 新しい状態が追加されるたびに publish() を修正する必要がある
  • 状態と処理が混在していて拡張に弱い

パターン別のリファクタリング

対応可能なデザインパターン例

パターン概要主な解決アプローチ
State状態ごとにオブジェクトを分け、振る舞いを委譲状態を明示的にクラスで管理
Strategy振る舞いを外部に差し替える状態を切り替える制御は外部任せ
Command状態による処理をコマンドオブジェクトで持つ実行内容をオブジェクト化し柔軟に制御