一,观察者模式

1、概念介绍

  观察者模式(Observer)完美的将观察者和被观察的对象分离开。举个例子,用户界面可以作为一个观察者,业务数据是被观察者,用户界面观察业务数据的变化,发现数据变化后,就显示在界面上。面向对象设计的一个原则是:系统中的每个类将重点放在某一个功能上,而不是其他方面。一个对象只做一件事情,并且将他做好。观察者模式在模块之间划定了清晰的界限,提高了应用程序的可维护性和重用性。

2、实现方式

  Observer模式有很多实现。基本上,模式必须包含两个角色:观察者和观察对象。在前面的示例中,业务数据是观察对象,用户界面是观察者。观察者和观察者之间存在逻辑关系。随着观察者的变化,观察者观察到这些变化并作出相应的反应。如果在用户界面和业务数据之间使用此类观察过程,则可以确认界面和数据已明确定义。假设应用程序需要更改,您需要更改接口的性能。用户界面,业务数据需要重建。不需要改变。

二、案例分析

  为了更直观地去理解观察者模式,笔者在这里选用github上一个“可暂停的观察者模式”项目进行分析,帮助读者更加直观地去理解观察者模式在软件中的作用。该项目的github地址为https://github.com/virtualnobi/PausableObserverPattern

class PausableObservable(ObserverPattern.Observable): 
    """
  这是一个可以暂停的观察者对象,可以暂停和恢复更新过程的观察者对象。

  暂停哪些更新可以取决于:
  1、可观察的类或实例
  2、要更新的部分
  3、观察者的类或实例

  通过pasueUpdates()和resumeUpdates()来控制暂停的更新。
""" PausedTriples = [] # Class Methods @classmethod def pauseUpdates(clas, observable, aspect, observer): """
     暂停更新的实现。

     如果observable, aspect, observer为None,则它充当于一个通配符,意味着它可以匹配任意字符。

     observable暂停所有来源于(from)此对象的更新(如果它是一个类,则暂停所有实例的更新)

     字符串/Unicode方面指定要暂停的方面

     observer暂停此对象上(at)的所有更新(如果它是一个类,则暂停所有实例的更新)
""" if ((aspect <> None) and (not isinstance(aspect, str)) and (not isinstance(aspect, unicode))): raise TypeError, 'pauseUpdates(): aspect must be either None, str or unicode!' clas.PausedTriples.append((observable, aspect, observer)) @classmethod def resumeUpdates(clas, observable, aspect, observer): """
     按照指定进行更新。

     observable, aspect, observer三方面必须对应于先前调用pasueUpdates()的参数,否则会抛出异常。
""" toRemove = None for triple in clas.PausedTriples: if ((triple[0] == observable) and (triple[1] == aspect) and (triple[2] == observer)): toRemove = triple break if (toRemove): clas.PausedTriples.remove(toRemove) else: raise ValueError def doUpdateAspect(self, observer, aspect): """
     如果未暂停更新,请调用观察者的updateAspect()方法。
""" stop = False for triple in self.__class__.PausedTriples: if (self.matches(triple[0], self) and ((triple[1] == None) or (triple[1] == aspect)) and self.matches(triple[2], observer)): print('PausableObservable: Paused update of aspect "%s" of %s to %s' % (aspect, self, observer)) stop = True break if (not stop): observer.updateAspect(self, aspect)

def matches(self, matchingSpec, matchingObject): """
     检擦对象是否与给定的规范匹配。
       如果对象等于matchingSpec或它的类,则匹配。若匹配规则缺失,则可以匹配任意对象。
       返回一个布尔值。
""" return((None == matchingSpec) or (matchingSpec == matchingObject) or (inspect.isclass(matchingSpec) and isinstance(matchingObject, matchingSpec))) # Class Initialization pass # Executable Script if __name__ == "__main__": pass

 

  可以看出,该项目通过pauseUpdates() and resumeUpdates()两个函数实现了对被观察的对象的暂停与恢复更新,而pauseUpdates(),resumeUpdates()与doUpdateAspect()实现了观察者的操作,通过这些函数,实现了一个简单的观察者模式,并且可以自主操控暂停与恢复更新。

posted on 2018-10-26 21:52  txblsalb  阅读(181)  评论(0编辑  收藏  举报