👻
デザインパターンを学ぶ #15 Prototype(プロトタイプ)
1. はじめに
今回は Prototype(プロトタイプ)パターン。
目的は、既存のオブジェクトをコピーして新しいオブジェクトを作ることです。
コンストラクタで複雑な初期化が必要なオブジェクトでも、ひな形(プロトタイプ)から複製することで高速かつ柔軟に生成できます。
2. Prototypeとは?
プロトタイプパターンは、**オブジェクトの生成を new ではなく「複製」で行う」**という考え方です。
- 同じ構造・値を持ったインスタンスを複数作りたい
-
clone()
などを使ってコピーする
というような場面で使われます。
主な登場役は以下の2つです:
- Prototype(原型) … 自分自身を複製できる
- Client(利用側) … Prototypeを複製して利用する
3. 実装イメージ(PHP)
<?php
// Prototype(原型)
abstract class DocumentPrototype {
public function __construct(
protected string $title,
protected string $content
) {}
abstract public function copy(): static;
public function dump(): string {
return "{$this->title}: {$this->content}";
}
}
// ConcretePrototype(具体的原型)
class Report extends DocumentPrototype {
public function copy(): static {
return clone $this;
}
}
// --- 実行例 ---
$report1 = new Report('週報', '今週の進捗...');
$report2 = $report1->copy();
$report3 = $report1->copy();
echo $report1->dump(), PHP_EOL; // 週報: 今週の進捗...
echo $report2->dump(), PHP_EOL; // 週報: 今週の進捗...
echo $report3->dump(), PHP_EOL; // 週報: 今週の進捗...
4. メリット・デメリット
メリット
- 複雑な初期化処理を省略できる
- new を使わずに柔軟にインスタンス生成できる
デメリット
- 深いコピー・浅いコピーの扱いを間違えるとバグになる
- 複雑なオブジェクトではコピー実装が難しい
5. 使いどころ
- 複雑な初期化処理が必要なオブジェクトを大量に生成したいとき
- テンプレート(ひな形)を元に複製して使いたいとき
- インスタンス生成コストを下げたいとき
「newせずに複製して作る」というアプローチが、プロトタイプパターンです。
Discussion