生成器模式的定义:将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
我们先来看一个简单的例子,比如说Product类是一个复杂的类,构建它需要许多步骤
class Product { List<string> parts = new List<string>(); public void Add(string part) { //添加产品部件 parts.Add(part); } }
我们需要定义一个抽象的生成器类Builder,来定义构建Product的步骤
abstract class Builder { public abstract void BuildPartA(); public abstract void BuildPartB(); public abstract void BuildPartC(); public abstract void BuildPartD(); public abstract Product GetResult(); }
我们需要定义具体的生成器类ConcreteBuilderOne、ConcreteBuilderTwo来实现Builder (即复杂对象的表示)
abstract class ConcreteBuilderOne { private Product product = new Product(); public override void BuildPartA() { product.Add("添加部件A"); } public override void BuildPartB() { product.Add("添加部件B"); } public override void BuildPartC() { product.Add("添加部件C"); } public override void BuildPartD() { product.Add("添加部件D"); } public override Product GetResult() { return product; } }
abstract class ConcreteBuilderTwo { private Product product = new Product(); public override void BuildPartA() { product.Add("添加部件A"); } public override void BuildPartB() { product.Add("添加部件B"); } public override void BuildPartC() { product.Add("添加部件C"); } public override void BuildPartD() { product.Add("添加部件D"); } public override Product GetResult() { return product; } }
接下来我们需要定义一个叫Director的类,我们叫它指挥者类(它负责复杂对象的构建)
class Director { public void Construct(Builder builder) { builder.BuildPartA(); builder.BuildPartB(); builder.BuildPartC(); builder.BuildPartD(); } }
下面我们就可以在客户端构建对象了
static void Main(string[] args) { Director director = new Director(); Builder one = new ConcreteBuilderOne(); Builder two = new ConcreteBuilderTwo(); director.Construct(one); Product p1 = one.GetResult(); director.Construct(two); Product p2 = two.GetResult(); }
通过上面的代码可以很容易看出,生成器模式使得构建对象的过程独立出来放到指导者类里,它不负责具体每步的实现,具体的实现放到生成器类里,这样它们就分离开来了。指导者就是可以重用的构建过程,而生成器是可以被切换的具体实现。
生成器模式的结构图如下:
生成器模式的重心在于分离构建算法和具体的构造实现,从而使得构建算法可以重用。具体的构造实现可以很方便的扩展和切换。
值得一提的是,在前面的例子里,指导者仅仅是简单地调用了生成器的方法,实际上可能回事比较复杂的算法,指导者和生成器是需要交互的,比如:1.运行指导者时,会按照整体构建算法的步骤进行运算,可能先运算前几部,到了某一步,需要调用Builder创建某个部件对象了,在调用Builder时可能会把前面运算的数据传给Builder。2.Builder创建好部件对象后可能需要返回该对象供指导者使用。 3.如此反复下去,直到整个构建算法运行完成,最终产品也就创建完了。
生成器模式的本质:分离整体构建算法和部件构造。