乐趣区

关于javascript:设计模式之生成器模式

生成器模式又叫做建造者模式,之前介绍的一些创立型的设计模式根本都比较简单的,生成器模式是较为简单的创立型模式,它将客户端与蕴含多个组成部分的简单对象的创立过程拆散,客户端毋庸晓得简单对象的外部组成部分与拆卸形式,只须要晓得所需建造者的类型即可。

它关注如何一步一步创立一个的简单对象,不同的具体建造者定义了不同的创立过程,且具体建造者互相独立,减少新的建造者十分不便,毋庸批改已有代码,零碎具备较好的拓展性。

什么是生成器模式

生成器模式:是一种设计模式,又名:建造模式,是一种对象构建模式。它能够将简单对象的建造过程形象进去(形象类别),使这个形象过程的不同实现办法能够结构出不同体现(属性)的对象。—— 节选自维基百科

例如,咱们来思考如何创立一辆汽车对象。发明一辆简略的汽车,首先须要创立车的框架和车轱辘,而后装置汽车门、汽车玻璃,最初再装置上发动机。然而如果你想要一个性能更好的汽车的话,那么还须要给汽车加上一些其余的设施,这个时候咱们须要怎么去做呢?

最简略的办法是拓展原有汽车的基类,而后创立一系列涵盖所有参数组合的子类。但最终将面对相当数量的子类。任何新增的参数都会让这个层次结构更加简单。

另一种办法则无需生成子类。能够再汽车的基类中创立一个包含所有可能参数的超级构造函数,并用它来管制汽车对象。这种办法能够防止生成子类,但它却会造成另外一个问题。通常状况下,绝大部分的参数都没有应用,这使得对于构造函数的调用非常不简洁。

生成器模式优缺点

生成器模式会将对象结构过程划分为一组步骤,每次创建对象时,你都须要通过生成器对象执行一系列步骤。重点在于你无需调用所有步骤,而只需调用创立特定对象配置所需的那些步骤即可。当你须要创立不同模式的产品时,其中的一些结构步骤可能须要不同的实现。能够创立多个不同的生成器,用不同形式实现一组雷同的创立步骤。而后你就能够在创立过程中应用这些生成器(例如按顺序调用多个结构步骤)来生成不同类型的对象。

长处

  1. 在生成器模式中,客户端不用晓得产品外部组成的细节,将产品自身与产品的创立过程解耦,使得雷同的创立过程能够创立不同的产品对象。
  2. 每一个具体建造者都绝对独立,而与其余的具体建造者无关,因而能够很不便地替换具体建造者或减少新的具体建造者,用户应用不同的具体建造者即可失去不同的产品对象。因为指挥者类针对形象建造者编程,减少新的具体建造者毋庸批改原有类库的代码,零碎扩大不便,合乎 开闭准则
  3. 能够更加精密地管制产品的创立过程。将简单产品的创立步骤合成在不同的办法中,使得创立过程更加清晰,也更方便使用程序来管制创立过程。

毛病

  1. 生成器模式所生成的产品个别具备较多的共同点,其组成部分类似,如果产品之间的差异性很大,例如很多组成部分都不雷同,不适宜应用建造者模式,因而其应用范畴受到肯定的限度
  2. 如果产品的外部变动简单,可能会导致须要定义很多具体建造者类来实现这种变动,导致系统变得很宏大,减少零碎的了解难度和运行老本

示例

生成器模式的次要角色如下:

  1. 生成器:接口生命再所有类型生成器中通用的产品结构步骤
  2. 具体生成器:提供结构过程的不同实现。具体生成器也能够结构不遵循通用接口的产品
  3. 产品:是最终生成的对象。由不同生成器结构的产品无需属于同一类档次结构或接口
  4. 指挥者:定义调用结构步骤的程序,这样你就能够创立和服用特定的产品配置
  5. 客户端:必须将某个生成器对象与主管类关联,个别状况下,你只须要通过指挥者类构造函数的参数进行一次性关联即可

类图如下所示:

代码示例:

// 形象建造者
abstract class Builder {public abstract buildPartA():void;
    public abstract buildPartB():void;
    public abstract buildPartC():void;
    public abstract buildProduct():Product;}

// 具体建造者
class ConcreteBuilder extends Builder {
    private product:Product;
    constructor(product:Product) {super();
        this.product = product;
    }

    public buildPartA():void {}
    public buildPartB():void {}
    public buildPartC():void {}

    // 最终组建一个产品
    public buildProduct():Product {return this.product;}
}

// 产品角色
class Product {public doSomething():void {// 独立业务}
}

// 指挥者
class Director {
    private _builder:Builder;
    constructor(builder:Builder) {this._builder = builder;}

    set builder(builder:Builder) {this._builder = builder;}

    // 将解决建造的流程交给指挥者
    public constructorProduct() {this._builder.buildPartA();
        this._builder.buildPartB();
        this._builder.buildPartC();
        return this._builder.buildProduct();}
}

// 应用
const builder:Builder = new ConcreteBuilder(new Product());
const director:Director = new Director(builder);
const product:Product = director.constructorProduct();

总结

生成器模式的次要性能是构建简单的产品,而且是细化的,分步骤的构建产品,也就是生成器模式重在一步一步解决结构简单对象的问题。如果仅仅这么认知生成器模式的性能是不够的。更为重要的是,这个构建的过程是对立的、固定不变的,变动的局部放到生成器局部了,只有配置不同的生成器,那么同样的构建过程,就能构建出不同的产品来。

尽管在生成器模式的整体构建算法中,会一步一步疏导 Builder 来构建对象,但这并不是说生成器次要就是用来实现分步骤构建对象的。生成器模式的重心还是在于拆散整体构建算法和部件结构,而分步骤构建对象不过是整体构建算法的一个简略体现,或者说是一个附带产物。

退出移动版