PHP设计模式装饰器与代理模式 PHP设计模式装饰器与代理模式装饰器模式和代理模式在结构上有点相似但目的完全不同。装饰器动态添加功能代理控制访问。今天用代码说明两者的区别。装饰器模式的核心是层层包装每个装饰器添加一点功能。phpinterface Notification{public function send(string $message): void;}class BasicNotification implements Notification{public function send(string $message): void{echo 发送消息: $message\n;}}abstract class NotificationDecorator implements Notification{protected Notification $notification;public function __construct(Notification $notification){$this-notification $notification;}}class EmailDecorator extends NotificationDecorator{private string $email;public function __construct(Notification $notification, string $email){parent::__construct($notification);$this-email $email;}public function send(string $message): void{$this-notification-send($message);echo 发送邮件至 {$this-email}: $message\n;}}class SmsDecorator extends NotificationDecorator{private string $phone;public function __construct(Notification $notification, string $phone){parent::__construct($notification);$this-phone $phone;}public function send(string $message): void{$this-notification-send($message);echo 发送短信至 {$this-phone}: $message\n;}}class LogDecorator extends NotificationDecorator{public function send(string $message): void{echo [日志] 开始发送\n;$this-notification-send($message);echo [日志] 发送完成\n;}}$notification new BasicNotification();$notification new EmailDecorator($notification, userexample.com);$notification new SmsDecorator($notification, 13800138000);$notification new LogDecorator($notification);$notification-send(系统更新通知);?代理模式在需要控制对象访问时使用。phpinterface Image{public function display(): void;}class RealImage implements Image{private string $filename;public function __construct(string $filename){$this-filename $filename;$this-loadFromDisk();}private function loadFromDisk(): void{echo 从磁盘加载图片: {$this-filename}\n;}public function display(): void{echo 显示图片: {$this-filename}\n;}}class ImageProxy implements Image{private ?RealImage $realImage null;private int $accessCount 0;public function __construct(private string $filename) {}public function display(): void{$this-accessCount;echo 第{$this-accessCount}次访问\n;if ($this-realImage null) {$this-realImage new RealImage($this-filename);}$this-realImage-display();}}$image new ImageProxy(photo.jpg);$image-display();$image-display();echo 访问次数: {$image-getAccessCount()}\n;?保护代理控制访问权限。phpinterface Document{public function getContent(): string;}class SecureDocument implements Document{private string $content;public function __construct(string $content){$this-content $content;}public function getContent(): string{return $this-content;}}class DocumentProxy implements Document{private ?SecureDocument $document null;private array $allowedRoles;public function __construct(string $content, array $allowedRoles){$this-document new SecureDocument($content);$this-allowedRoles $allowedRoles;}public function getContent(): string{$role $_SESSION[role] ?? guest;if (!in_array($role, $this-allowedRoles)) {throw new RuntimeException(权限不足);}return $this-document-getContent();}}?装饰器和代理的主要区别是用途不同。装饰器用于增强功能代理用于控制访问。装饰器接收被装饰对象作为参数代理则自己创建或引用目标对象。理解了这两种模式的区别在实际项目中就能根据需求选择合适的方案。