導入
デザインパターンは、ソフトウェア開発において再利用可能な解決策を提供します。特に中級エンジニアにとって、実際の業務において直面する問題を解決するための具体的な手法を理解することが重要です。本記事では、TypeScriptを用いて、特定のデザインパターンの実装方法とその応用例を紹介します。
教科書レベルの解説(デザインパターン)
重要な概念の整理
デザインパターンの中でも、特に「ストラテジーパターン」は、アルゴリズムの選択をクライアントから分離するために用いられます。このパターンを利用することで、異なるアルゴリズムを持つクラスを簡単に切り替えられるようになります。たとえば、異なる種類のデータを処理する際に、異なる処理ロジックを持つクラスを動的に切り替えることができます。
コード例(TypeScript)
interface SortingStrategy {
sort(data: number[]): number[];
}
class QuickSort implements SortingStrategy {
sort(data: number[]): number[] {
// クイックソートの実装
if (data.length <= 1) return data;
const pivot = data[data.length - 1];
const left = data.slice(0, -1).filter(x => x < pivot);
const right = data.slice(0, -1).filter(x => x >= pivot);
return [...this.sort(left), pivot, ...this.sort(right)];
}
}
class BubbleSort implements SortingStrategy {
sort(data: number[]): number[] {
const arr = [...data];
for (let i = 0; i < arr.length; i++) {
for (let j = 0; j < arr.length - i - 1; j++) {
if (arr[j] > arr[j + 1]) {
[arr[j], arr[j + 1]] = [arr[j + 1], arr[j]];
}
}
}
return arr;
}
}
class Context {
private strategy: SortingStrategy;
constructor(strategy: SortingStrategy) {
this.strategy = strategy;
}
setStrategy(strategy: SortingStrategy) {
this.strategy = strategy;
}
sortData(data: number[]): number[] {
return this.strategy.sort(data);
}
}
// 使用例
const data = [5, 3, 8, 1, 2];
const context = new Context(new QuickSort());
console.log(context.sortData(data)); // クイックソートを使用
context.setStrategy(new BubbleSort());
console.log(context.sortData(data)); // バブルソートに切り替え
コードの行ごとの解説
- SortingStrategyインターフェースを定義し、ソートアルゴリズムの契約を示します。
- QuickSortクラスは、クイックソートアルゴリズムを実装し、
sortメソッドを提供します。 - BubbleSortクラスは、バブルソートアルゴリズムを実装し、同様に
sortメソッドを持ちます。 - Contextクラスは、現在の戦略を保持し、データをソートするためのメソッドを提供します。
- 最後に、クライアントコードでコンテキストを生成し、戦略を設定し、データをソートします。
練習問題編
以下の練習問題を解いて、デザインパターンの理解を深めましょう。
- 問題1: ストラテジーパターンを用いて、異なるフィルタリングアルゴリズムを実装するクラスを作成してください。
- 問題2: ストラテジーパターンを利用して、データのソート方法を動的に変更する機能を追加してください。
- 問題3: 上記のコードに新しいソートアルゴリズムを追加し、クライアントコードでそのアルゴリズムを使用してください。
まとめ
- ストラテジーパターンを使用すると、異なるアルゴリズムを簡単に切り替えられる。
- TypeScriptでの実装は、他の言語にも応用可能であり、柔軟性を持たせることができる。
- 実際の業務で遭遇する問題に対して、デザインパターンを適用することで、コードの可読性と再利用性が向上する。