Ответ
Декоратор — это структурный паттерн, позволяющий динамически добавлять объектам новую функциональность, оборачивая их в объекты-декораторы. Основная проблема, которую он решает — расширение поведения объекта без изменения его исходного кода и без создания подклассов.
Пример с кэшированием:
interface DataProvider {
public function fetchData(): array;
}
class DbDataProvider implements DataProvider {
public function fetchData(): array {
return ['data' => 'from db'];
}
}
class CacheDecorator implements DataProvider {
private $provider;
private $cache;
public function __construct(DataProvider $provider) {
$this->provider = $provider;
}
public function fetchData(): array {
if ($this->cache) return $this->cache;
$this->cache = $this->provider->fetchData();
return $this->cache;
}
}
// Использование
$provider = new CacheDecorator(new DbDataProvider());
$data = $provider->fetchData(); // Будет закешировано
Плюсы:
- Гибкость: можно комбинировать декораторы
- Открытость/закрытость: не изменяем исходный класс
- Чистая композиция вместо наследования