行为型模式是对在不一样对象之间划分责任和算法的抽象化。正则表达式
行为模式不只仅关于类和对象,还关于它们之间的相互做用。算法
行为型模式又分为类的行为模式和对象的行为模式两种。编程
行为型模式包括11种模式: 模板方法模式、命令模式、迭代器模式、观察者模式、中介者模式、状态模式、策略模式、责任链模式、访问者模式、解释器模式、备忘录模式数据结构
在一个抽象类中定义一个操做算法的骨架,将一些步骤延迟到子类中去实现。模板方法使得子类能够在不改变算法结构的情冴下,从新定义算法中的某些步骤。框架
一般咱们会遇到这样的一个问题:咱们知道一个算法所需的关键步聚,并肯定了这些步聚的执行顺序。可是某些步聚的具体实现是未知的,或者是某些步聚的实现与具体的环境相关。工具
模板方法模式把咱们不知道具体实现的步聚封装成抽象方法,提供一些按正确顺序调用它们的具体方法(这些具体方法统称为模板方法),这样构成一个抽象基类,子类经过继承这个抽象基类去实现各个步聚的抽象方法,而工做流程却由父类来控制。性能
定不变的封装到抽象类中,须要改变的在子类中去实现。.net
经常使用场景:一批子类的功能有可提取的公共算法骨架设计
选择关键点:算法骨架是否牢固server
命令模式的本质是对命令进行封装,将发出命令的责任和执行命令的责任分割开
每个命令都是一个操做:请求的一方发出请求,要求执行一个操做;接收的一方收到请求,并执行操做。
命令模式容许请求的一方和接收的一方独立开来,使得请求的一方没必要知道接收请求的一方的接口,更没必要知道请求是怎么被接收,以及操做是否被执行、什么时候被执行,以及是怎么被执行的。
命令模式的关键在于引入了抽象命令接口,且发送者针对抽象命令接口编程,只有实现了抽象命令接口的具体命令才能与接收者相关联。
迭代器模式提供了一种方法顺序访问一个聚合对象(理解为集合对象)中各个元素,而又无需暴露该对象的内部表示,这样既能够作到不暴露集合的内部结构,又可以让外部代码透明地访问集合内部的数据。 迭代器模式为遍历不一样的汇集结构提供如开始、下一个、是否结束、当前哪一项等统一的接口。
当你须要访问一个聚合对象,并且无论这些对象是什么都须要遍历的时候,就应该考虑使用迭代器模式。另外,当须要对汇集有多种方式遍历时,能够考虑去使用迭代器模式。
聚合对象,如须要操做。则额外创建一个迭代器类。对集合进行操做处理,其实.net框架已经准备好了迭代器接口,只须要实现接口就好了IEumerator 支持对非泛型集合的简单迭代。
使用迭代器的好处就是在于保持良好的封装的同时对集合元素进行循环操做。不须要把数据集合展示给外部对象。不使用迭代器,外部对象会经过getter的方法获取数据集合而后遍历,这样把整个数据集合公开了,而且外部对象能够直接改写,另外遍历数据集合时也要知道数据结构,先分析数据结构才能进行迭代代码的书写,这样若是下次须要修改数据结构时,代码修改也会变的困难。
观察者模式又叫发布订阅模式,定义了一种一对多的依赖关系,让多个观察者对象同时监听某一个主题对象,这个主题对象在状态发生变化时,会通知全部观察者对象,使它们可以自动更新本身的行为。
将一个系统分割成一系列相互协做的类有一个很很差的反作用,那就是须要维护相关对象间的一致性,咱们不但愿为了维持一致性而使各个类紧密耦合,这样会给维护,扩展和重用都带来不便。而观察者模式的关键对象是主题Subject和观察者Obverser,一个Subject能够任意数目依赖它的Obverser,一旦Subject的状态发生变化,全部的Obverser都合一获得通知。Subject发出通知时,并不须要知道谁是它的观察者,也就是说,具体观察者是谁,它根本不须要知道,而任何一个具体的观察者不知道也不须要知道其余观察者的存在。
Subject类是把因此观察者对象的引用保存在一个汇集里,每一个主体均可以有任意数量的观察者,抽象主体提供一个借口,能够增长和删除观察者对象.是个主题或者抽象统治者,Obverser类是抽象观察者,为全部的具体观察者定义一个接口,在获得主题的通知时更新本身,ConcreteSubject类是具体主题,讲有关状态存入具体观察者对象,在具体主题的内部状态改变时,给全部登记过的观察者发出通知,ConcreteObserver类是具体观察者,实现抽象观察者所要求的更新接口,一遍使自己的状态与主题的状态相协调
观察者模式所作的工做其实就是在解除耦合,让耦合的双方都依赖于抽象,而不是依赖于具体,从而使得各自的变化都不会影响另外一边的变化。
当一个对象的改编须要同时改变其余对象的时候,并且它不知道具体有多少对象有待改变时,应该考虑使用观察者模式。须要将观察者与被观察者解耦或是观察者的种类不肯定
选择关键点:观察者与被观察者是不是多对一的关系
定义了一个中介对象来封装一系列对象之间的交互关系。中介者使各个对象之间不须要显式地相互引用,从而使耦合性下降,并且能够独立地改变它们之间的交互行为
对象与对象之间存在大量的关联关系,这样势必会致使系统的结构变得很复杂,同时若一个对象发生改变,咱们也须要跟踪与之相关联的对象,同时作出相应的处理。同时若一个对象发生改变,咱们也须要跟踪与之相关联的对象,同时作出相应的处理。系统的可扩展性低。增长一个新的对象,咱们须要在其相关连的对象上面加上引用,这样就会致使系统的耦合性增高,使系统的灵活性和可扩展都下降。
封装一个中介对象来封装系列对象之间的交互。中介者使各个对象不须要显示地相互引用,从而使其耦合性松散,并且能够独立地改变他们之间的交互
由此咱们能够看出中介者对象封装了对象之间的关联关系,致使中介者对象变得比较庞大,所承担的责任也比较多,它须要知道各个对象交互的细节,若是它出现问题,将致使整个系统的瘫痪。故当系统中出现“多对多”的交互复杂的关系群时,千万别着急使用中介者模式,须要先分析下在设计上是否合理
主要包括抽象中介者和具体中介者 抽象同事类 和具体同事类
当一个对象的行为取决于它的状态,而且它必须在运行时刻根据状态改变它的行为时,就能够考虑使用状态模式了
所谓的状态模式是容许对象在内部状态发生改变时改变它的行为,对象看起来好像修改了它的类
状态模式主要解决的是当控制一个对象状态转换的条件表达式国语复杂时的状况,把状态的判断逻辑转移到表示不一样状态的一系列类当中,能够把复杂的判断逻辑简化。固然,若是这个状态判断 很简单,那就没有必要用状态模式了。状态模式的好处就是将与特定状态相关的行为局部化,而且将不一样状态的行为分隔开来
因为状态的改变,会改变派生类,产生不一样的重载方法。
经常使用场景:一个对象在多个状态下行为不一样,且这些状态可互相转换
选择关键点:这些状态是否常常在运行时须要在不一样的动态之间相互切换
状态模式与职责链模式的区别:状态模式是让各个状态对象本身知道其下一个处理的对象是谁,即在编译时便设定好了的;而职责链模式中的各个对象并不指定其下一个处理的对象究竟是谁,只有在客户端才设定。
策略模式是针对一组算法,将每一个算法封装到具备公共接口的独立的类中,从而使它们能够相互替换。策略模式使得算法能够在不影响到客户端的状况下发生变化。
定义了一个公共接口,各类不一样的算法以不一样的方式实现这个接口,Context使用这个接口调用不一样的算法,通常使用接口或抽象类实现。
应用场景:
策略模式提供了管理相关的算法族的办法。策略类的等级结构定义了一个算法或行为族。恰当使用继承能够把公共的代码转移到父类里面,从而避免重复的代码。
策略模式提供了能够替换继承关系的办法。继承能够处理多种算法或行为。若是不是用策略模式,那么使用算法或行为的环境类就可能会有一些子类,每个子类提供一个不一样的算法或行为。可是,这样一来算法或行为的使用者就和算法或行为自己混在一块儿。决定使用哪种算法或采起哪种行为的逻辑就和算法或行为的逻辑混合在一块儿,从而不可能再独立演化。继承使得动态改变算法或行为变得不可能。
使用策略模式能够避免使用多重条件转移语句。多重转移语句不易维护,它把采起哪种算法或采起哪种行为的逻辑与算法或行为的逻辑混合在一块儿,通通列在一个多重转移语句里面,比使用继承的办法还要原始和落后。
客户端必须知道全部的策略类,并自行决定使用哪个策略类。这就意味着客户端必须理解这些算法的区别,以便适时选择恰当的算法类。换言之,策略模式只适用于客户端知道全部的算法或行为的状况。策略模式形成不少的策略类,每一个具体策略类都会产生一个新类。有时候能够经过把依赖于环境的状态保存到客户端里面,而将策略类设计成可共享的,这样策略类实例能够被不一样客户端使用。换言之,可使用享元模式来减小对象的数量。
责任链模式(Chain of Responsibility Pattern)为请求建立了一个接收者对象的链。这种模式给予请求的类型,对请求的发送者和接收者进行解耦。
某个请求须要多个对象进行处理,从而避免请求的发送者和接收之间的耦合关系。将这些对象连成一条链子,并沿着这条链子传递该请求,直到有对象处理它为止。这些对象由每个对象对其下家的引用而链接起来造成一条链。一般每一个接收者都包含对另外一个接收者的引用。若是一个对象不能处理该请求,那么它会把相同的请求传给下一个接收者,依此类推。
经常使用场景:一个请求的处理须要多个对象当中的一个或几个协做处理。
优势:下降耦合度。它将请求的发送者和接收者解耦。简化了对象。使得对象不须要知道链的结构。增长新的请求处理类很方便。加强给对象指派职责的灵活性。经过改变链内的成员或者调动它们的次序,容许动态地新增或者删除责任。
可是不能保证请求必定被接收。可能不容易观察运行时的特征,有碍于除错。
访问者模式就是表示一个做用于某对象结构中的各元素的操做。它使你能够在不改变各元素的类的前提下定义做用于这些元素的新操做。
访问者适合于数据结构相对比较稳定的系统,主要是把处理从数据结构分离出来,不少系统能够按照算法和数据结构分开,若是这样的系统有比较稳定的数据结构,又有易于变化的算法的话,使用访问者模式就比较合适,由于访问者模式使得算法的增长变得容易。
访问者模式的优势是增长新的操做很容易,由于增长新的操做就意味这增长了一个新的访问者,访问者模式将有关的行为集中到一个访问者对象中
访问者的缺点实际上是使增长新的数据结构变的很困难
在不破坏封装的前提下,捕获一个对象的内部状态,并在该对象以外保存这个状态,这样之后就能够把该对象恢复到原先的状态。发起人能够根据须要决定备忘录存储本身的哪些内部状态。
经常使用场景:须要在对象的外部保存该对象的内部状态
解释器模式描述了如何为简单的语言定义一个文法,如何在该语言中表示一个句子,以及如何解释这些句子。
.当有一个语言须要解释执行,而且你可将该语言中的句子表示为一个抽象语法树,可使用解释器模式。而当存在如下状况时该模式效果最好
解释器模式真的是一个比较少用的模式,由于对它的维护实在是太麻烦了,想象一下,一坨一坨的非终结符解释器,假如不是事先对文法的规则了如指掌,或者是文法特别简单,则很难读懂它的逻辑。解释器模式在实际的系统开发中使用的不多,由于他会引发效率、性能以及维护等问题,尽可能不要在重要模块中使用解释器模式,由于维护困难。在项目中,可使用脚本语言来代替解释器模