概要
パターンとは「コードに名前を与え、設計の意図を共有する技術」である。
JavaScriptにおいても、デザインパターンは構造・振る舞い・生成方法を明示化するための設計言語として機能する。
本稿では、実用性が高く現代JSにも適した5つのパターンを解説する:
- Observer(監視者)
- Factory(生成)
- Strategy(戦略)
- Singleton(単一性)
- Command(命令オブジェクト)
1. Observer パターン:変化の伝播
✅ 使いどころ:状態変化の通知、多対多の依存関係
class Subject {
constructor() {
this.observers = [];
}
subscribe(fn) {
this.observers.push(fn);
}
notify(data) {
this.observers.forEach(fn => fn(data));
}
}
// 利用例
const store = new Subject();
store.subscribe((val) => console.log('変更検知:', val));
store.notify({ count: 1 });
→ ✅ 状態の変化を購読させ、疎結合でリアクティブな構造を実現
2. Factory パターン:生成の抽象化
✅ 使いどころ:条件によって異なるインスタンス生成、newの隠蔽
function createUser(role) {
if (role === 'admin') {
return { role, permissions: ['ALL'] };
} else {
return { role, permissions: ['READ'] };
}
}
const admin = createUser('admin');
→ ✅ インスタンス生成ロジックを隠蔽し、呼び出し側の責務を軽減
3. Strategy パターン:振る舞いの切り替え
✅ 使いどころ:アルゴリズムを切り替え可能にする
class Sorter {
constructor(strategy) {
this.strategy = strategy;
}
sort(arr) {
return this.strategy(arr);
}
}
const bubbleSort = arr => [...arr].sort();
const quickSort = arr => [...arr].sort((a, b) => a - b);
const sorter = new Sorter(quickSort);
console.log(sorter.sort([3, 1, 2]));
→ ✅ アルゴリズムを関数として外部化し、再利用性と切替性を確保
4. Singleton パターン:インスタンスの一意性保証
✅ 使いどころ:状態を共有したいがインスタンスは1つでいいとき
const Logger = (() => {
let instance;
function create() {
return { log: (msg) => console.log('[Log]', msg) };
}
return {
getInstance: () => {
if (!instance) instance = create();
return instance;
}
};
})();
Logger.getInstance().log('初回');
Logger.getInstance().log('同じインスタンス');
→ ✅ アプリケーションスコープでの状態共有やキャッシュに最適
5. Command パターン:処理の抽象化・遅延実行
✅ 使いどころ:操作を“オブジェクト”として定義し、キュー制御やUndoを可能に
class Command {
constructor(execute, undo) {
this.execute = execute;
this.undo = undo;
}
}
const queue = [];
function runCommand(cmd) {
cmd.execute();
queue.push(cmd);
}
function undoLast() {
const cmd = queue.pop();
if (cmd) cmd.undo();
}
// 使用例
const logCmd = new Command(
() => console.log('実行'),
() => console.log('取り消し')
);
runCommand(logCmd); // 実行
undoLast(); // 取り消し
→ ✅ 処理の“記録・再生・取り消し”が可能に
パターン適用判断フロー
① 状態変化を通知したい? → Observer
② 条件で生成物が変わる? → Factory
③ アルゴリズムを切り替えたい? → Strategy
④ インスタンスを1つに制限したい? → Singleton
⑤ 実行ロジックを外部化したい? → Command
よくあるミスと対策
❌ パターンを使うことが目的化している
→ ✅ パターンは“構造を整理するための手段”である
→ “自作パターン”が必要なこともある
❌ 密結合な構成のままObserverを導入
→ ✅ 発火元と購読者を完全に疎結合に設計
❌ 使い捨てコードにSingletonを導入
→ ✅ 永続性・共有性がある前提のときだけ使う
結語
パターンとは、設計の言語である。
ただの構文やテクニックではなく、“どう構造を分けるか”という思想をコードに落とすための手段である。
- Observerは伝える
- Factoryは隠す
- Strategyは選ばせる
- Singletonは統一する
- Commandは委ねる
設計は、ただ正しく書くのではなく、“正しく分ける”ことで生まれる。
パターンはその分け方を支える、コード設計の言語である。