设计模式5——创建型模式之建造者模式

定义: 建造者模式(Builder Pattern),  将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。

类型:创建型模式。

类图

 

参与角色:

    1. Product,定义了一组产品的部件,并且有一个方法来表示对象。
    2. Builder,提供一系列Product对象每个部件构成的接口。
    3. BuilderA、BuilderB通过实现父类的接口来完成产品各部分的构造。
    4. Director,构造使用Builder接口的对象。

概述

        产品的不同,是由具体的构建过程不同造成的,所以把每个产品不同的地方抽象出来。这样不同产品,就不需要用派生新的产品类来完成,只需要匹配不同的构建过程类即可。Builder只是完成从产品中分离出来的每个小部件的生成的接口。具体的创建顺序以及创建逻辑则由Director控制。理论上是可以不要Director,而直接由Builder的派生类来完成的。Director的作用是利用Builder提供的接口,按一定规则,选择一定的部件来完成产品的建造。

         一个好的示例对于理解建造者模式非常重要。很多书上的示例还是有些过于复杂。而网络上的一些示例,有很多表达得并不是很清晰,没有吃透建造者模式的关键点。

         建造者,我这里举一个与房屋建造有关的示例,能够比较好地诠释建造者模式的关键点。下面结合代码一点一点来分析。

代码

// Product:产品是带装修的房子,这里的装修列得比较简单,列了几个代表性的装修点

 1 class CHouse
 2 {
 3 public:
 4     void Show()
 5     {
 6         cout<<m_strFloor<<endl;
 7         cout<<m_strCeiling<<endl;
 8         cout<<m_strWall<<endl;
 9     }
10 public:
11     string m_strFloor; 
12     string m_strCeiling; 
13     string m_strWall;
14 };

 

// Builder,即抽象出产品不同的原因,即具体装修点的装修不同造成的。

// 那么就把这几个不同装修点的装修过程抽象出来作为一个类

// 另外该类还实现了产品的新建、销毁以及获取产品

 1 class CDecoration
 2 {
 3 public:
 4     void CreateHouse()
 5     {
 6         m_pHouse = new CHouse();
 7     }
 8     void DestoryHouse()
 9     {
10         delete m_pHouse;
11         m_pHouse = NULL;
12     }
13     CHouse* GetHouse()
14     {
15         return m_pHouse;
16     }
17     virtual void SetFloor(){}
18     virtual void SetCeiling(){}
19     virtual void SetWall(){}
20 
21 protected:
22     CHouse* m_pHouse;
23 };

 

// BuilderA,在这里即复古风装修

// 具体实现Decoration的几个虚函数来完成复古风的的每个部件的生成。

 1 class CVintageDecoration : public CDecoration
 2 {
 3 public:
 4     void SetFloor()
 5     {
 6         m_pHouse->m_strFloor = "安装红木地板";
 7     }
 8 
 9     void SetCeiling()
10     {
11         m_pHouse->m_strCeiling = "安装复古风顶灯";
12     }
13 
14     void SetWall()
15     {
16         m_pHouse->m_strWall = "安装中国山水风格壁画";
17     }
18 };

 

// BuilderB,在这里即时尚风装修

// 同样是具体实现Decoration的几个虚函数来完成复古风的的每个部件的生成。

 1 class CFashionDecoration : public CDecoration
 2 {
 3 public:
 4     void SetFloor()
 5     {
 6         m_pHouse->m_strFloor = "安装实木地板";
 7     }
 8 
 9     void SetCeiling()
10     {
11         m_pHouse->m_strCeiling = "安装时尚大吊灯";
12     }
13 
14     void SetWall()
15     {
16         m_pHouse->m_strWall = "张贴亮丽鲜艳壁画";
17     }
18 };

 

// Director,指导如何按步骤地去完成房屋的装修,另外还可以分精装修,简装修,甚至是其它装修方式

// 就是根据Builder提供的接口来完成指定要求的装修

 1 class CDirector
 2 {
 3 public:
 4     // 精装修,地板,墙壁,天花板都装修
 5     void RefineDecorate(CDecoration* _pDecorate)
 6     {
 7         _pDecorate->CreateHouse();
 8         _pDecorate->SetFloor();
 9         _pDecorate->SetCeiling();
10         _pDecorate->SetWall();
11     }
12 
13     // 简装,只装修地板
14     void SimpleDecorate(CDecoration* _pDecorate)
15     {
16         _pDecorate->CreateHouse();
17         _pDecorate->SetFloor();
18     }
19 };

 

// 具体客户端的使用情况

 1 int _tmain(int argc, _TCHAR* argv[])
 2 {
 3     CHouse* pHouse = NULL;   
 4     CDirector director;
 5 
 6     // 小明的房子想要复古风的精装修
 7     CVintageDecoration vintageBuilder;
 8     director.RefineDecorate(&vintageBuilder);
 9     pHouse = vintageBuilder.GetHouse();
10     pHouse->Show();
11     vintageBuilder.DestoryHouse();
12 
13     // 小雷的房子暂时只想要复古风的简装修
14     director.SimpleDecorate(&vintageBuilder);
15     pHouse = vintageBuilder.GetHouse();
16     pHouse->Show();
17     vintageBuilder.DestoryHouse();
18 
19     // 小红的房子想要时尚风的精装修
20     CFashionDecoration fashionBuilder;
21     director.RefineDecorate(&fashionBuilder);
22     pHouse = vintageBuilder.GetHouse();
23     pHouse->Show();
24     fashionBuilder.DestoryHouse();
25 
26     // 小梅的房子也只想要时尚风的简装
27     director.SimpleDecorate(&fashionBuilder);
28     pHouse = vintageBuilder.GetHouse();
29     pHouse->Show();
30     fashionBuilder.DestoryHouse();
31 
32     return 0;
33 }

 

优缺点:

  1. 优点,从构建方式上抽象出不同的产品来,最大限度地展现了OOP抽象的作用。另外可以结合工厂方法模式,定制不同的Director,这样就可以得到不同的产品。
  2. 缺点,如果产品的表示变化了,那么一系列类都需要变动。

参考资料

  1. 《设计模式——可复用面向对象软件基础》
  1. Java与模式》
  1. 《大话设计模式》

 

源代码下载

posted @ 2014-01-08 20:00  飞鹤0755  阅读(602)  评论(0编辑  收藏  举报