2021-06-29 设计模式复习

一、创建型模式:不让用户依赖于对象的创建或排列方式

〇简单工厂模式

概念:Simple Factory模式根据提供给它的数据,返回几个可能类中的一个类的实例。通常它返回的类都有一个公共的父类和公共的方法。
-本质:选择实现
优点/缺点:

优点:
-帮助封装
  -简单工厂虽然很简单,但是非常友好的帮我们实现了组件的组装,然后让组件外部能真正的面向对象编程。
-解耦
  -通过简单工厂,实现了客户端和具体实现类的解耦。  
 缺点:
 -可能增加客户端的复杂度
 -不方便扩展子工厂

①工厂方法模式

-概念:定义一个用于创建对象的接口,让子类决定实例化哪一个类
-本质:延迟到子类来选择实现

-工厂方法模式与简单工厂模式:

-工厂方法模式与简单方法模式在结构上的不同不是很明显
-工厂方法类的核心时一个抽象工厂类,而简单工厂模式把核心放在一个具体类上。
-工厂方法模式有一个别名叫多态性工厂模式,因为具体工厂类都有共同的接口或者有共同的抽象父类

-优点\缺点:

 -优点:当系统扩展需要添加新的产品对象时,仅仅需要添加一个具体对象以及一个具体工厂对象,原有厂对象不需要进行任何修改,也不需要(尽量小的)修改客户端,较好的符合了“开放——封闭”原则。而简单工厂模式在添加新产品对象后不得不修改工厂方法,扩展性不好。
 -缺点:具体产品对象与工厂方法的耦合性
           工厂方法是要创建产品对象的,也就是需要选择具体的产品对象,并创建他们的实例。因此具体产品对象与工厂方法是耦合的。

-何时使用工厂方法模式

      -如果个类需要创建某个接口的对象,但是又不知道具体的实现,这种情况可以选用工厂方法模式,把创建对象的工作延迟到子类中实现
      -如果一个类本身就希望由他的子类来创建所需的对象的时候,应该使用工厂方法模式

-对设计原则的体现

 -工厂方法模式很好的体现了“依赖倒置原则”
    -依赖倒置原则告诉我们“要依赖抽象,不要依赖于具体类”,简单点说就是:不能让高层组件依赖于低层组件,而目不管高层组件还是低层组件,都应该依赖于抽象。
    -对于ExportOperate来说,它不关心具体的实现方式,它只是“面向接口编程”;对于具体的实现来说,它只关心自己“如何实现接有”所要求的功能。

②抽象工厂模式

-概念:提供一个对象,创建一系列或者相互依赖对象的接口,而无须指定它们具体的类
-本质:选择产品簇的实现
-优点/缺点:

 优点:
   -分离接口实现
   -使得切换产品簇变得更容易
 缺点:
   -不太容易扩展新的产品
   -容易造成类层次复杂

-什么情形下使用抽象工厂模式:

    -希望一个系统不应当依赖于产品类实例如何被创建、组合和表达的细节时。
    -一个系统有多于一个的产品族,而系统只消费其中某一产品族

③生成器(建造者)模式:

-概念:将一个复杂的对象的构建与它的表示分离,同样的构建可以创建不同的表示
(思路:先把构建过程独立出来,在建造者模式中把它称为指导者,由他来指导装配过程,但不负责每步具体的实现。
要有能具体实现每步的对象,称之为建造者或者生成器

-本质:分离整体构建算法和部件构造
-使用情形:

-需要生成的产品对象有复杂的内部结构。
-需要生成的产品对象的属性相互依赖,建造者模式可以强迫生成顺序。
-在对象创建过程中会使用到系统中的一些其它对象,这些对象在产品对象的过程中不易得到。

-优点/缺点:

-优点:
  -建造者模式的使用使得产品的内部表象可以独立的变化。【可以容易的改变产品的内部表示】
    使用建造者模式可以使客户端不必知道产品内部组成的细节。
-每一个Builder都相对独立,而与其它的Builder无关。【松散耦合】
-模式所建造的最终产品更易于控制。【更好的复用性】

④原型模式:

-概念:用原型实例指定创建对象的种类,并通过复制这些原理创建新的对象
-本质:克隆生成对象
-总结:

  -原型模式通过复制原型而获得新对象创建的功能,这里原型本身就是“对象工厂”(因为能够生产对象)
  -原型模式就是从自身复制自己创建的新对象

-优/缺点:

   -优点:
      -原型模式允许动态增加或减少产品类。
        由于创建产品类实例的方法是产品类内部具有的,因此增加新产品对整个结构没有影响。
      -原型模式提供了简化的创建结构。
        工厂方法模式常常需要有一个与产品类等级结构相同的等级结构,而原型模式就不需要这样。
    -缺点:
        原型模式的最主要缺点就是每个原型的子类都必须实现clone的操作,
        尤其在包含引用类型的对象时,clone方法会比较麻烦,必须要能够递归地让所有的相关对象都要正确地实现克隆

与工厂模式比较:

-原型模式在功能上可以代替工厂模式
-工厂模式实现生产产品的功能关键是利用了继承特性。也就是说,你生成的产品,一定是由同一个抽象产品类派生出来的。所以,在工厂模式下,你如果要生成一类产品,就要引入一个抽像产品类,然后再由它派生出具体产品。
-实际上,在原型模式中,每个具体产品就扮演了工厂模式里的具体工厂的角色(因为每个具体产品都具有生成自己拷贝的功能,从这种意义上讲,这正是工厂的作用。

⑤单例模式:

-概念:保证一个类仅有一个实例,并提供它的一个全局访问点
-本质:控制实例数目
-分类:

-懒汉式单例模式(时间换空间)
-饿汉式单例模式(空间换时间)

-特点:

    -单例类只能有一个实例
    -单例类必须自己创造自己的唯一实例
    -单例类必须给所有其它对象提供这一实例

-使用情形:

  -使用单例模式有一个必要条件:
    在一个系统要求一个类只有一个实例时才应当使用单例模式。
    反过来,如果一个类可以有几个实例共存,就不要使用单例模式。

二、行为型模式:合理地设计对象之间地交互通信,让设计富有弹性,易维护,易复用

①职责链:

-概念:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系
-本质:分离职责,动态组合
-优点/缺点:

  -优点:
    -请求者和接收者松散耦合
    -动态组合职贵
  -缺点:
    -产生很多细粒度对象
    -不一定能被处理
      -需要提供默认处理

-职责链模式和状态模式:

 -状态模式是一个对象的内在状态发生改变,一个对象相对比较稳定,处理完一个对象下一个对象的处理一般都已确定。
 -职责链模式过于灵活,在客户端使用时,需要环境去确定下一个对象是谁,一些列的set操作......。职责链模式是多个对象之间的改变,就会出现某个对象不存在的情景。

②命令模式

-概念:将一个请求封装为一个对象,从而可用不同的请求对客户进行参数化,对请求排队或记录日志,以及支持可撤销操作

-本质:封装请求

-使用情形:

    -如果需要在不同的时刻指定、排列和执行请求,可以选用命令模式,
     把这些请求封装成为命令对象,然后实现把【请求队列化】
    -如果需要【支持取消操作】,可以选用命令模式,
     通过管理命令对象,能很容易的实现命令的恢复和重做的功能。
    -如果需要支持当系统崩溃时,能把对系统的操作动能重新执行一遍,
     可以选用命令模式,把这些操作场能的请求封装成命令对象,然后实现日志命令,就可以在系统恢复回来后,通过日志获取命令列表,从而重新执行一遍功能。
    -在【需要事务】的系统中,可以选用命令模式,
     命令模式提供了对事务进行建模的方法,命令模式有一个别名就是Transaction。

-命令模式的优点:

命令允许请求的一方和接收请求的一方能够独立演化,从而有以下的优点:
  -命令模式使新的命令很容易地被加入到系统里。
  -允许接收请求的一方决定是否要否决(Veto)请求。
  -能较容易地设计一个命令队列。
  -可以容易地实现对请求的Undo和Redo。
  -在需要的情况下,可以较容易地将命令记入日志。
  -命令模式把请求一个操作的对象与知道怎么执行一个操作的对象分割开。
  -命令类与其他任何别的类一样,可以修改和推广。

③迭代器模式

-概念:提供一种方法顺序访问某一个聚合对象中的各个元素,而不需要暴露该对象的内部表示
-本质:逐一遍历
-总的来说,迭代器模式就是分离了集合对象的遍历行为,抽出一个具体迭代器类来负责,这样既可以不暴露集合内部的结构,又可以让外部代码透明的访问集合内部的数据。
-使用情形:
需要聚合对象有多种方式遍历

④中介者模式

-概念:用一个中介对象来封装一系列对象的交互。中介者使各对象不需要显示地相互引用,从而使其耦合松散,而且可以独立地改变它们之间地交互。
-本质:封装交互
-优点:

   -将多对多通信转换成一对多,降低了系统负责性
   -获得系统解耦性
   -控制集中

⑤备忘录模式:

-概念:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样以后就可以将该对象恢复到原先保存的状态。
-本质:保存和恢复内部状态
-优点/缺点:

 优点:
    -发起人内部信息对其他对象屏蔽,保持封装的边界线
    -简化了发起人类
    -可以实现状态复原
缺点:
    -有可能占用较大的存储空间

与原型模式结合起来使用:

⑥观察者模式:

-概念:定义了一种一对多的依赖关系,当一个对象的状态发生变化时,所有依赖于它的对象都得到通知并被自动更新
-本质:触发联动
-优点/缺点:

  -优点:
   -观察者模式实现了观察者和目标之间的抽象耦合。
    -观察者模式卖现了动态联动
    -观察者模式支持广播通信。被观察者会向所有的登记过的观察者发出通知。
  -缺点:
    -可能会引起无谓的操作。
      由于采用广播方式,不管观察者需不需要,每个观察者都会被调用update方法。

⑦状态模式:

-概念:允许一个对象在其内部状态改变时改变他的行为,对象看起来似乎改变了他的类
-本质:根据状态来分离和选择行为,状态模式就是状态驱动,由上下文负责
-优点/缺点:

-优点:
    -将与特定状态相关的行为局部化,并且将不同状态的行为分割开来
    -消除庞大的条传分支语句,把各种状态转移逻辑分布到State的子类之间,减少了相互间的依赖。
    -显式化进行状态转换:为不同的状态引入独立的对象,使得状态的转换变得要加明确。而且状态对象可以保证上下文不会发生内部状态不一致的状况,因为上下文中只有一个变量来记录状态对象,只要为这一个变量赋值就可以了。
  -缺点:
    -State模式问题主要是逻辑分散化,状态逻辑分布到了很多的State的子类中,很难看到整个的状态逻辑图,这也带来了代码的维护问题。

⑧策略模式:

-概念:定义一系列算法,把它们一个个封装起来,并且使它们可以相互替换。本模式使算法可以独立于使用它的客户而变化
-本质:分离算法,选择实现
-模式讲解:

 -策略模式功能:把具体算法从具体业务处理中独立
    -策略模式与if-e se语句:
      多个if-else出现考虑使用策略模式算法的平等性
    -谁来选择具体策略算法:客户端 由上下文来选择具体的策略算法

-使用情形:

-出现同一个算法,有很多不同的实现的情况,可以使用策略模式来把这些“不同的实现”实现成为一个算法的类层次
-出现抽象一个定义了很多行为的类,并且是通过多个if-else语句来选择这些行为的情况,可以使用策略模式来代替这些条件语句

-优点/缺点:

  -优点:
    -策略模武可以避免让客户端涉及到不必要接触到的复杂的和只与算法有关的数据。
    -避免使用难以维护的多重条件选择语句
    -更好的扩展
  -缺点:
    -上述策略模式,把分支判断又放回到客户端,要改变需求算法时,还是要去更改客户端的程序
    -客户端必须知道所有的策略类,并自行决定使用哪一个策略类。这就意味着客户端必须理解这些算法的区别从以便适时选择恰当的算法类。
    -导致:
        -增加了对象的数目
        -只适合扁平的算法结构

⑨模板方法模式:

-概念:定义一个操作中算法的骨架,而将一些步骤延迟到子类中。模板方法使字类可以不改变一个算法的结构即可重定义该算法的某些特定步骤
-本质:父类定义框架,子类具体处理

-优点/缺点:

 -优点:
      -实现代码复用
 -缺点:
      -算法骨架不容易升级人模板和子类是非常耦合的,如要对模板中的算法骨架进行变更,会影响子类变化

⑩访问者模式:

-概念:表示一个作用于某对象结构中的各个元素的操作。它可以在不改变各个元素的类的前提下定义作用于这些元素的新操作
-本质:预留通路,回调实现
-在元素稳定时使用

三、结构型模式:涉及如何组合类和对象,以形成更大的结构,和类有关的结构型对象如何合理的使用继承机制;和对象有关的结构型模型涉及如何合理地使用对象组合机制

①适配器模式:

-概念:将一个类地接口转换成客户希望地另一个接口。适配器模式使原本由于接口不兼容而不能一起工作的类,一起工作。
 -本质:统一叶子对象与组合对象
-两种形式:类的适配器模式、对象的适配器模式(主要)

-使用场景:

 -系统需要使用现有的类,而此类的接口不符合系统的需要。
 -想要建立一个可以重复使用的类,该类可能与其它不相关的类或不可预见的类(即那些接口可能不一定兼容的类)协同工作。
 -(对对象适配器而言)在设计里,你想使用一些已经存在的子类,但是不可能对每一个子类都进行适配。对象适配器可以适配它们的父类接口(使用的扩展)。

优点/缺点:

-优点:
  -更好的复用性
  -更好的可扩展性
    -在实现适配器功能的时候,可以调用自己开发的功能,从而自然地扩展系统的功能
-缺点:
  -过多地使用适配器,会让系统非常凌乱,不容易整体进行把握。
-本质:转换匹配,复用功能

②组合模式:

-概念:将对象组合成数形结构以表示“部分——整体”的层次结构。Composite使用户对单个对象和组合对象的使用具有一致代表性
-本质:统一叶子对象与组合对象

-优点:


-组合模式中包含个体对象和组合对象,并形成树形结构,使用户可以方便地处理个体对象和组合对象。
-当组合对象和个体对象实现了相同的接口,用户一般无须区分个体对象。
-当增加新的Composite节点和Leaf节点时,用户的重要代码不需要做出修改。

-透明方式:实现Component接口的所有子类中具有Add和Remove方式
-安全方式:实现Component接口的所有子类中不具有Add和Remove方式

-使用情形:

 -当需求中体现部分与整体的结构层次
 -希望用户可以忽略组合对象和单个对象的不同,统一的使用组合结构中所有的对象

③代理模式:

-概念:为其他对象提供一种代理以控制这个对象的访问
-本质:控制对象的访问
-应用:

  -远程代理
  -虚拟代理
  -安全代理

④享元模式:

-概念:运用共享技术有效的支持大量细粒度对象
-本质:分离与共享
-认识享元:

-变与不变
  -享元模式设计的重点就在分离变与不变。把一个对象的状态分成内部状态和外部状态,内部状态是不变的,外部状态是可变的。然后通过共享不变的部分,达到减少对象数量并节约内存的目的
  -分离变与不变是软件设计上最基本的方式之一,比如预留接口:一个常见的原因就是这里存在变化,可能在今后需要扩展或者是改变已有的实现,因此预留接口作为“可插入性的保证”。

-使用场景:

  -一个系统有大量的对象。这些对象耗费大量的内存。
  -这些对象的状态中的大部分都可以外部化。
  -这些对象可以按照内部状态分成很多的组,当把外部对象从对象中剔除时,每一个组都可以仅用一个对象代替。
满足以上的这些条件的系统可以使用享元对象。
  -使用享元模式需要维护一个记录了系统已有的所有享元的表,而这需要耗费资源。因此,应当在有足够多的享元实例可供共享时才值得使用享元模式。

【享元模式在编辑器系统中大量使用】
优点/缺点:

-优点:
  -大幅度地降低内存中对象的数量,节省内存空间。
-缺点:
  -享元模式使得系统更加复杂,为了使对象可以共享,需要将一些状态外部化,这使得程序的逻辑复杂化。
  -享元模式将享元对象的状态外部化,而读取外部状态使得运行时间变长。

⑤外观模式:
-概念:为系统中的一组接口提供一个一致的界面,外观模式定义了一个高层的接口,这个接口使这一子系统更加容易使用
-本质:封装交互,简化调用

-使用场景:

   -当客户程序与抽象类的实现部分之间存在着很大的依赖性时,引入Facade将这个子系统与客户以及其他的子系统分离,为一个复杂子系统提供一个简单接口,Facade可以提供一个简单的缺省视图,这一视图对大多数用户来说已经足够,而那些需要更多的可定制性的用户可以越过Facade层。可以提高子系统的独立性和可移植性。
    -在层次化结构中,可以使用Facade模式定义系统中每一层的入口点,如果子系统之间是相互依颗的,则以让他们仅通过Facade进行通信,从而简化他们之间的依赖关系。
    -希望包装或隐藏原有系统:Facade可以把原有系统作为自己的私有成员。原有系统Facade类联系在一起,但使用Facade类的客户无法看到原有的系统。
      -维护一个遗留的大型系统。
      -跟踪对系统的使用---强迫所有客户通过Facade使用原有系统。

-优点/缺点:

   -优点:
      -屏敝了外部客户端和系统内部模块的交互Facade的功能可以被多个客户端调用
      -可以实现复用(功能的共享)
      -对使用Facade的大员来说,Facade大大的节省了他们的学习成本
    -缺点:不符合开闭原则

⑥桥接模式:

-概念:将抽象部分与它的实现分离,使它们都可以独立的变化
-本质:分离抽象实现
-两个等级结构:
  -由抽象化角色和修正抽象化角色组成的抽象化等级结构。 
  -由实现化角色和两个具体实现化角色所组成的实现化等级结构。

⑦装饰模式:

-概念:动态地给对象添加一些额外地职责,就功能来说装饰模式相比生成子类更灵活
 -本质:动态组合:动态是手段,组合是目的
-模式讲解:
  -装饰模式的功能
    -能够实现动态地为对象添加功能,是从一个对象外部来给对象增加功能,相当于是改变了对象的外观。
  -对象组合
    -Favor Composition Over Inheritance。装饰模式的思考起点就是这个规则。
  -装饰器和组件类的关系
    -装饰器是用来装饰组件的,装饰器一定要实现和组件类一致的接口,保证他们是同一个类型,并具有同一个外观,这样组合完成的装饰才能够递归调用下去

-优点/缺点:

   -优点:
      -装饰模式与继承关系的目的都是要扩展对象的功能,但是装饰模式可以提供比继承更多的灵活性。
      -通过使用不同的具体装饰类以及这些装饰类的排列组合,设计师可以创造出很多不同行为的组合。
    -缺点:会产生很多细粒度对象

-应用场景:

-如果需要在不影响其他对象的情况下,以动态、透明的方式给对象添加职责,可以使用装饰模式
-如果不适合使用子类来进行扩展的时候(比如:扩展功能需要的子类太多,造成子类数目的爆炸性增长),可以考虑使用装饰模式
  -因为装饰模式时使用“对象组合”的方式。

-装饰模式和策略模式:

  -策略模式改变的是对象的内核
  -装饰模式政变的是对象的外壳
  -策略模式是一层递归
  -装饰模式是递归调用
  -可以有机结合
      -可以在一个具体的装饰器里面使用策略模式,来选择更具体的实现方式。

-装饰模式与组合模式:

-这两个模式有相似之处,都涉及到对象的递归调用,可以把装饰看成是只有一个组件的组,
-它们的目的完全不一样:
  -装饰模式是要动态的给对象增加功能
  -组合模式是想要管理组合对象和叶子对象,为它们提供一个一致的操作接口给客户端,方便客户端的使用。

-装饰模式与模板方法模式:

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值