Перейти к основному содержимому

Что это такое

Паттерн Прототип создаёт новые объекты путём клонирования уже существующего, а не сборки с нуля. Вы готовите один объект как шаблон, затем копируете его ключевым словом PHP clone и меняете только то, что отличается.

Главное, что нужно учесть: обычный clone копирует свойства-значения, но вложенные объекты остаются общими, а не копируются. Метод __clone() копирует их заново, и тогда клон действительно независим.


Пример: шаблон документа

Шаблон несёт те части, которые повторяются в каждом документе. clone копирует его — а __clone() заново копирует вложенный объект TagList — поэтому правка копии не затрагивает шаблон.

Клонируйте, затем меняйте отличия

Отчёт получил новый заголовок и дополнительный тег, а в шаблоне по-прежнему только [draft] — потому что __clone() скопировал список тегов, а не сделал его общим.

Prompt
Напишите PHP-скрипт с классом Document (title, footer и объект TagList, содержащий массив tags) и методом __clone, который клонирует также TagList, чтобы клонированный документ был полностью независимым. Клонируйте шаблон в отчёт, измените title отчёта и добавьте тег, затем выведите оба документа, чтобы показать, что шаблон не изменился.
Вывод: PHP-скрипт

Когда использовать

Используйте, когда новые объекты в основном представляют собой копии заранее подготовленного — документы из шаблона, игровые сущности из спаунера, тестовые данные из фикстуры.

Не используйте, когда объекты дёшево создать заново или когда в них нет ничего общего. Для объекта из простых значений — строк, чисел, массивов — обычный clone в PHP уже даёт полную копию, и __clone() не нужен.


Плюсы и минусы

Плюсы: дешёвое создание предварительно настроенных объектов; шаблон документирует значения по умолчанию; никакого повторяющегося кода настройки.

Минусы: в глубоком копировании легко допустить незаметную ошибку — забытое свойство-объект тихо связывает клон и оригинал; со временем клоны незаметно расходятся с шаблоном.