PHP设计模式 五 (观察者 策略 装饰器模式)

来源:互联网 发布:淘宝卖家用什么app聊天 编辑:程序博客网 时间:2024/06/05 19:23

观察者模式

观察者模式(有时又被称为发布-订阅Subscribe>模式、模型-视图View>模式、源-收听者Listener>模式或从属者模式)是软件设计模式的一种。在此种模式中,一个目标物件管理所有相依于它的观察者物件,并且在它本身的状态改变时主动发出通知。这通常透过呼叫各观察者所提供的方法来实现。此种模式通常被用来实现事件处理系统。
当一个对象的状态发生改变时,依赖他的对象全部会接到通知,并自动更新。观察者模式实现了低耦合 非入侵式的通知与更新机制。

观察者模式示例:
首先创建一个事件生成器 EventGenerator.php

<?phpnamespace Components\ObServer;abstract class EventGenerator {private $obServers = array();function addObServer(IObServer $obServer) {//添加事件$this->obServers[] = $obServer;}function notify() {foreach ($this->obServers as $obServer) {//一一执行更新$obServer->update();}}}

创建一个观察者接口IObServer.php
<?phpnamespace Components\ObServer;interface IObServer {function update($event_info = NULL);}

事件主体:
class Event extends \Components\ObServer\EventGenerator{function tringger() {echo "<br>Event<br/>";$this->notify();}}

观察者:
//观察者1class ObServer1 implements \Components\ObServer\IObServer {function update($event_info = null) {echo "logic1<br>";}}//观察者2class ObServer2 implements \Components\ObServer\IObServer {function update($event_info = null) {echo "logic2<br>";}}

触发:
$event = new Event();$event->addObServer(new ObServer1());$event->addObServer(new ObServer2());$event->tringger();




策略模式

将一组特定的行为和算法封装成类,以适应某些特定的上下文环境,这就是策略模式。

应用场景:
1、 多个类只区别在表现行为不同,可以使用Strategy模式,在运行时动态选择具体要执行的行为。
2、 需要在不同情况下使用不同的策略(算法),或者策略还可能在未来用其它方式来实现。
3、 对客户隐藏具体策略(算法)的实现细节,彼此完全独立。

组成
1、抽象策略角色: 策略类,通常由一个接口或者抽象类实现。
2、具体策略角色:包装了相关的算法和行为。
3、环境角色:持有一个策略类的引用,最终给客户端调用。

分类广告策略示例:
抽象策略角色
vim Istrategy.php

<?phpnamespace Components\Strategy;/** * 策略模式 接口 * @author YUNDUAN * */interface IStrategy{function showAd();function showCategory();}

具体策略角色
vim FemaleUser.php
<?phpnamespace Components\Strategy;class FemaleUser implements IStrategy {function showAd() {echo '女性广告<br>';}function showCategory() {echo '女装<br>';}}

vim MaleUser.php
<?phpnamespace Components\Strategy;class MaleUser implements IStrategy {function showAd() {echo '男性广告<br>';}function showCategory() {echo '电子产品<br>';}}

环境角色:
vim Home.php
/** * 策略模式 解耦和 * @author YUNDUAN * */class Home {protected $strategy;function index() {echo "AD:";$this->strategy->showAd();echo "Category:";$this->strategy->showCategory();}function setStrategy(Components\Strategy\IStrategy $strategy) {                //依赖注入   注入一个对象$this->strategy = $strategy;}}

使用:
$home = new Home();if (isset($_GET['female'])) {$strategy = new \Components\Strategy\FemaleUser();}else {$strategy = new \Components\Strategy\MaleUser();}/*策略模式*/$home->setStrategy($strategy);$home->index();



装饰器模式

在不必改变原类文件和使用继承的情况下,动态地扩展一个对象的功能。它是通过创建一个包装对象,也就是装饰来包裹真实的对象。

装饰器接口IDecorator.php:

<?phpnamespace Components\Decorator;/** * 装饰器模式  接口 * @author WH * */interface IDecorator {function before();function after();}


装饰器1 DecoratorAttr1.php:
<?phpnamespace Components\Decorator;class DecoratorAttr1 implements IDecorator{function before() {echo '<br><div style="color:red">';}function after() {echo '</div>';}}


装饰器2  DecoratorAttr2.php:
<?phpnamespace Components\Decorator;class DecoratorAttr2 implements IDecorator{function before() {echo '<br><div style="font-size:30px">';}function after() {echo '</div>';}}

使用:
/* 装饰器模式 原类 */class DecoratorClassTest {protected $decorators = array();//添加装饰器function addDecorator(\Components\Decorator\IDecorator $decorator) {$this->decorators[] = $decorator;//添加装饰器}function before(){foreach ($this->decorators as $decorator) {$decorator->before();//调用装饰器}}function after(){//这里可用栈$decorators = array_reverse($this->decorators);foreach ($decorators as $decorator) {$decorator->after();//结束装饰器}}function test() {$this->before();echo 'running<be>';$this->after();}}

$decoratorTest = new DecoratorClassTest();$decoratorTest->addDecorator(new \Components\Decorator\DecoratorAttr1());$decoratorTest->addDecorator(new \Components\Decorator\DecoratorAttr2());$decoratorTest->test();



策略模式

将一组特定的行为和算法封装成类,以适应某些特定的上下文环境,这就是策略模式。

应用场景:
1、 多个类只区别在表现行为不同,可以使用Strategy模式,在运行时动态选择具体要执行的行为。
2、 需要在不同情况下使用不同的策略(算法),或者策略还可能在未来用其它方式来实现。
3、 对客户隐藏具体策略(算法)的实现细节,彼此完全独立。

组成
1、抽象策略角色: 策略类,通常由一个接口或者抽象类实现。
2、具体策略角色:包装了相关的算法和行为。
3、环境角色:持有一个策略类的引用,最终给客户端调用。

分类广告策略示例:
抽象策略角色
vim Istrategy.php

<?phpnamespace Components\Strategy;/** * 策略模式 接口 * @author YUNDUAN * */interface IStrategy{function showAd();function showCategory();}

具体策略角色
vim FemaleUser.php
<?phpnamespace Components\Strategy;class FemaleUser implements IStrategy {function showAd() {echo '女性广告<br>';}function showCategory() {echo '女装<br>';}}

vim MaleUser.php
<?phpnamespace Components\Strategy;class MaleUser implements IStrategy {function showAd() {echo '男性广告<br>';}function showCategory() {echo '电子产品<br>';}}

环境角色:
vim Home.php
/** * 策略模式 解耦和 * @author YUNDUAN * */class Home {protected $strategy;function index() {echo "AD:";$this->strategy->showAd();echo "Category:";$this->strategy->showCategory();}function setStrategy(Components\Strategy\IStrategy $strategy) {                //依赖注入   注入一个对象$this->strategy = $strategy;}}

使用:
$home = new Home();if (isset($_GET['female'])) {$strategy = new \Components\Strategy\FemaleUser();}else {$strategy = new \Components\Strategy\MaleUser();}/*策略模式*/$home->setStrategy($strategy);$home->index();

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 u盘突然无法识别怎么办 u盘电脑无法识别怎么办 系统无法识别u盘怎么办 手机u盘无法识别怎么办 u盘无法被识别怎么办 电脑不能读取u盘怎么办 电脑装系统卡了怎么办 怀孕三个月胚胎停育怎么办 被蟑螂咬了怎么办图片 有家人进了传销怎么办 有亲人进了传销怎么办 误入传销违法了怎么办 tt游戏账号忘了怎么办 被臭蚊子咬了怎么办 狗狗鼻子掉皮了怎么办 火碱弄到皮肤上怎么办 蓝斑马鱼怀孕后怎么办 汽油喝到肚子里怎么办 加了不好的汽油怎么办 不小心喝了汽油怎么办 如果误喝了汽油怎么办 小孩误喝了汽油怎么办 欠债活不下去了怎么办 待产住院住早了怎么办 狗狗一天吃一顿怎么办 四个月宝宝消化不好怎么办 内火旺盛长痘怎么办 我有恋爱恐惧症怎么办 白鹤芋叶子蔫了怎么办 白掌叶子蔫了怎么办 鱼塘的鱼不吃食怎么办 新买的鱼不吃食怎么办 养的鱼不吃食怎么办 罗汉掉鳞还是洞怎么办 刚买的鱼不吃食怎么办 锦鲤鱼掉鱼鳞片怎么办 锦鲤鱼身上烂了怎么办 鱼掉了一片鳞是怎么办 地图鱼身上烂了怎么办 小腿上有鱼鳞皮怎么办 食道里长了息肉怎么办