观察者模式有时也被称作发布/订阅模式,该模式用于为对象实现发布/订阅功能:一旦主体对象状态发生改变,与之关联的观察者对象会收到通知,并进行相应操作。
将一个系统分割成一个一些类相互协作的类有一个不好的副作用,那就是需要维护相关对象间的一致性。我们不希望为了维持一致性而使各类紧密耦合,这样会给维护、扩展和重用都带来不便。观察者就是解决这类的耦合关系的。
消息队列系统、事件都使用了观察者模式。
业务场景:
哈票以购票为核心业务(此模式不限于该业务),但围绕购票会产生不同的其他逻辑,如:
1、购票后记录文本日志
2、购票后记录数据库日志
3、购票后发送短信
4、购票送抵扣卷、兑换卷、积分
5、其他各类活动等
传统解决方案:
在购票逻辑等类内部增加相关代码,完成各种逻辑。
观察者模式典型实现方式:
1、定义2个接口:观察者(通知)接口、被观察者(主题)接口
2、定义2个类,观察者对象实现观察者接口、主题类实现被观者接口
3、主题类注册自己需要通知的观察者
4、主题类某个业务逻辑发生时通知观察者对象,每个观察者执行自己的业务逻辑。
示例代码:
观察者接口:
interface TicketObserver {
//得到通知后调用的方法
public function onBuyTicketOver($sender, $args);
}
被观察者接口:
interface TicketObservable {
//提供注册观察者方法
public function addObserver($observer);
}
观察者:
//短信通知
class MSM implements ITicketObserver {
public function onBuyTicketOver($sender, $ticket) {
echo "短信通知";
}
}
//push通知
class Push implements ITicketObserver {
public function onBuyTicketOver($sender, $ticket) {
echo "push通知";
}
}
被观察者:
class Ticket implements TicketObservable {
private $_comsumer;
private $_observers = array (); //观察者
//购票流程
public function buyTicket($ticket) {
// TODO 购票逻辑
//循环通知,调用其onBuyTicketOver实现不同业务逻辑
foreach ( $this->_observers as $obs )
$obs->onBuyTicketOver ( $this->_comsumer, $ticket );
}
//添加通知
public function addObserver($observer) {
$this->_observers [] = $observer;
}
}
网友评论