ThinkChat2.0新版上线,更智能更精彩,支持会话、画图、阅读、搜索等,送10W Token,即刻开启你的AI之旅 广告
[toc] ## 举个例子 **程序员为了找女朋友, 开始注意着装和形象了...** * 头上带一副方形黑框眼镜。 * 上面是一件紫红色针织毛衣,内套一件白色衬衫; * 下面是一条卡其色休闲裤配一双深色休闲皮鞋,加一条银色针扣头的黑色腰带; * 整体行装虽不潮流,却透露出一种工作人士的成熟、稳健和大气! * 人还是那个人, 不同的着装, 体现不同的性格和形象. ## 代码示例 ```php <?php // 人 class Person { private $name; public function __construct($name) { $this->name = $name; } public function getName() { return $this->name; } public function wear() { echo "我的着装是:" . PHP_EOL; } } // 工程师 class Engineer extends Person { private $skill; public function __construct($name, $skill) { parent::__construct($name); $this->skill = $skill; } public function getSkill() { return $this->skill; } public function wear() { echo "我是" . $this->getSkill() . "工程师" . $this->getName() . PHP_EOL; parent::wear(); } } // 教师 class Teacher extends Person { private $title; public function __construct($name, $title) { parent::__construct($name); $this->title = $title; } public function getTitle() { return $this->title; } public function wear() { echo "我是" . $this->getName() . $this->getTitle() . PHP_EOL; parent::wear(); } } // 服装装饰器 class ClothingDecorator extends Person { protected $decorated; public function __construct($person) { $this->decorated = $person; } public function wear() { $this->decorated->wear(); } } // 休闲裤 class CasualPantDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一条卡其色休闲裤" . PHP_EOL; } } // 腰带 class BeltDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一条银色针扣头的黑色腰带" . PHP_EOL; } } // 皮鞋 class LeatherShoesDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一双深色休闲皮鞋" . PHP_EOL; } } // 针织毛衣 class KnittedSweaterDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一件紫红色针织毛衣" . PHP_EOL; } } // 白色衬衫 class WhiteShirtDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一件白色衬衫" . PHP_EOL; } } // 眼镜 class GlassesDecorator extends ClothingDecorator { public function __construct($person) { parent::__construct($person); } public function wear() { parent::wear(); echo "一副方形黑框眼镜" . PHP_EOL; } } $tony = new Engineer("Tony", "客户端"); $pant = new CasualPantDecorator($tony); $belt = new BeltDecorator($pant); $shoes = new LeatherShoesDecorator($belt); $shirt = new WhiteShirtDecorator($shoes); $sweater = new KnittedSweaterDecorator($shirt); $glasses = new GlassesDecorator($sweater); $glasses->wear(); echo PHP_EOL; $decorateTeacher = new GlassesDecorator(new WhiteShirtDecorator(new LeatherShoesDecorator(new Teacher("wells", "教授")))); $decorateTeacher->wear(); ``` ``` D:\soft\php72\php.exe D:\project\php_dp\index.php 我是客户端工程师Tony 我的着装是: 一条卡其色休闲裤 一条银色针扣头的黑色腰带 一双深色休闲皮鞋 一件白色衬衫 一件紫红色针织毛衣 一副方形黑框眼镜 我是wells教授 我的着装是: 一双深色休闲皮鞋 一件白色衬衫 一副方形黑框眼镜 Process finished with exit code 0 ``` ## 什么是装饰模式? > 动态地给一个对象增加一些额外的职责(Responsibility),就增加对象功能来说,装饰模式比生成子类实现更为灵活。 ![](https://box.kancloud.cn/e57b8047725caa41cd058a7f5e50d9cb_549x413.png) ## 模式特点 1. 可灵活地给一个对象增加职责或拓展功能 如上面的示例中,可任意地穿上自己想穿的衣服。不管穿上什么衣服,你还是那个你,但穿上不同的衣服你就会有不同的外表。 1. 可增加任意多个装饰 你可以只穿一件衣服,也可以只穿一条裤子,也可以衣服和裤子各种搭配的穿,全随你意! 1. 装饰的顺序不同,可能产生不同的效果 内裤穿在里面是正常人, 内裤外穿就变成了超人 ## 优缺点 **装饰模式的优点**: 1.使用装饰模式来实现扩展比继承更加灵活,它可以在不需要创造更多子类的情况下,将对象的功能加以扩展。 1. 可以动态地给一个对象附加更多的功能。 1. 可以用不同的装饰器进行多重装饰,装饰的顺序不同,可能产生不同的效果。 1. 装饰类和被装饰类可以独立发展,不会相互耦合;装饰模式相当于是继承的一个替代模式。 **装饰模式的缺点**: 1. 与继承相比,用装饰的方式拓展功能更加容易出错,排错也更困难。对于多次装饰的对象,调试时寻找错误可能需要逐级排查,较为烦琐。 ## 应用场景 1. 有大量独立的扩展,为支持每一种组合将产生大量的子类,使得子类数目呈爆炸性增长。 1. 需要动态地增加或撤销功能时。 1. 不能采用生成子类的方法进行扩充时,如类定义不能用于生成子类。