您的位置:首页 > 产品设计 > UI/UE

Builder 构建器模式

2009-10-25 21:13 190 查看
      Builder 构建模式要解决的是这样的问题:当我们要创建的对象很复杂的时候(通常是由很多其他的对象组合而成),我们要要复杂对象的创建过程和这个对象的表示(展示)分离开来,这样做的好处就是通过一步步的进行复杂对象的构建,由于在每一步的构造过程中可以引入参数,使得经过相同的步骤创建最后得到的对象的展示不一样。构建器模式和抽象工厂模式主要区别就是,构建器模式一步步创建对象,所以及时展开输出创建过程就似乎很重要。此外,“主管”(director)获得一个切片流(stream),并且将这些切片传递给构建器,每个切片用来执行创建过程的一步。
Builder 模式的典型通用结构类图如下:



参与者:
Builder:  为创建一个 Product 对象的各个部件指定抽象接口。
ConcreteBuilder: 不同的 Builder 实现. 1)实现 Builder 的接口以构造和装配该产品的各个部件。2)定义并确定它所创建的表示。3)提供一个检索产品的接口。
Director: 表示被构造的复杂对象。1)ConcreteBuilder 创建该产品的内部表示并定义它的装配过程。2)包含定义组成部件的对象,包括将这些部件装配成最终产品的接口。
协作:1)客户创建 Director 对象,并用它所想要的 Builder 对象进行配置。2)一旦产品部件被生成,导向器就会通知生成器。3)生成器处理导向器的请求,并将部件添加到该产品中。4)客户从生成器中检索产品。
注:在 Builder 中缺省方法为空。C++ 中,生成方法故意不声明为纯虚成员函数,而是把它们定义为空方法,这使客户只重定义他们所感兴趣的操作。
代码示例:
1://Builder.h


2:#pragma once


3:#include 


4: 


5:class Product;


6: 


7://构建器基类


8://成员函数故意不声明为纯虚函数,而是把它们定义为空方法


9://这样可以使子类只重定义感兴趣的操作.


10:class Builder


11:{


12:public:


13:virtual ~Builder();


14:virtual void BuildPartA(const std::string& buildPara){};


15:virtual void BuildPartB(const std::string& buildPara){};


16:virtual void BuildPartC(const std::string& buildPara){};


17:Product* GetProduct();


18:protected:


19:Builder();


20:};


21://具体的构建器1:ConcreteBuilder1


22:class ConcreteBuilder1: public Builder


23:{


24:public:


25:~ConcreteBuilder1();


26:void BuildPartA(const std::string& buildPara);


27:void BuildPartB(const std::string& buildPara);


28:void BuildPartC(const std::string& buildPara);


29: 


30:ConcreteBuilder1();


31:Product* GetProduct();


32:private:


33:Product* _product1;


34:};


35://具体的构建器2:ConcreteBuilder2


36:class ConcreteBuilder2: public Builder


37:{


38:public:


39:~ConcreteBuilder2();


40:void BuildPartA(const std::string& buildPara);


41:void BuildPartB(const std::string& buildPara);


42: 


43:ConcreteBuilder2();


44:Product* GetProduct();


45:private:


46:Product* _product2;


47:};


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://Director.h


2:#pragma once


3: 


4:class Builder;


5: 


6:class Director


7:{


8:public:


9:Director(Builder* b = 0);


10:~Director();


11:void Construct();


12:bool setBuilder(Builder* b);


13: 


14:private:


15:Builder* _bld;


16:};


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://Product.h


2:#pragma once


3:#include


4:#include 


5:#include


6: 


7:class ProductPart


8:{


9:public:


10:ProductPart(const std::string& part);


11:~ProductPart();


12:std::string* getPart() const;


13:private:


14:std::string* _part;


15:};//*/


16: 


17:class Product


18:{


19:private:


20:std::vector parts;


21:typedef std::vector partsVect;


22: 


23:public:


24:Product();


25:~Product();


26:void ProducePart(const std::string& str);


27:void displayPart();


28:};//*/


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://Builder.cpp


2:#include "Builder.h"


3:#include"Product.h"


4:#include


5: 


6://


7:Builder::Builder(){}


8:Builder::~Builder()


9:{


10://std::cout << "~Builder..." << std::endl;


11: 


12:}


13:Product* Builder::GetProduct()


14:{


15:return 0;


16:}


17://ConcreteBuilder1


18:ConcreteBuilder1::ConcreteBuilder1()


19:{


20://std::cout << "ConcreteBuilder1..." << std::endl;


21:_product1 = new Product;


22:}


23:ConcreteBuilder1::~ConcreteBuilder1()


24:{


25://std::cout << "~ConcreteBuilder1..." << std::endl;


26:}


27://


28:void ConcreteBuilder1::BuildPartA(const std::string& buildPara)


29:{


30:_product1->ProducePart(buildPara);


31:}


32:void ConcreteBuilder1::BuildPartB(const std::string& buildPara)


33:{


34:_product1->ProducePart(buildPara);


35:}


36:void ConcreteBuilder1::BuildPartC(const std::string& buildPara)


37:{


38:_product1->ProducePart(buildPara);


39:}


40: 


41:Product* ConcreteBuilder1::GetProduct()


42:{


43:return _product1;


44:}


45: 


46://ConcreteBuilder2


47:ConcreteBuilder2::ConcreteBuilder2()


48:{


49://std::cout << "ConcreteBuilder2..." << std::endl;


50:_product2 = new Product;


51:}


52:ConcreteBuilder2::~ConcreteBuilder2()


53:{


54://std::cout << "~ConcreteBuilder2..." << std::endl;


55:}


56://


57:void ConcreteBuilder2::BuildPartA(const std::string& buildPara)


58:{


59:_product2->ProducePart(buildPara);


60:}


61:void ConcreteBuilder2::BuildPartB(const std::string& buildPara)


62:{


63:_product2->ProducePart(buildPara);


64:}


65:Product* ConcreteBuilder2::GetProduct()


66:{


67:return _product2;


68:}


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://Builder.cpp


2:#include "Builder.h"


3:#include"Product.h"


4:#include


5: 


6://


7:Builder::Builder(){}


8:Builder::~Builder()


9:{


10://std::cout << "~Builder..." << std::endl;


11: 


12:}


13:Product* Builder::GetProduct()


14:{


15:return 0;


16:}


17://ConcreteBuilder1


18:ConcreteBuilder1::ConcreteBuilder1()


19:{


20://std::cout << "ConcreteBuilder1..." << std::endl;


21:_product1 = new Product;


22:}


23:ConcreteBuilder1::~ConcreteBuilder1()


24:{


25://std::cout << "~ConcreteBuilder1..." << std::endl;


26:}


27://


28:void ConcreteBuilder1::BuildPartA(const std::string& buildPara)


29:{


30:_product1->ProducePart(buildPara);


31:}


32:void ConcreteBuilder1::BuildPartB(const std::string& buildPara)


33:{


34:_product1->ProducePart(buildPara);


35:}


36:void ConcreteBuilder1::BuildPartC(const std::string& buildPara)


37:{


38:_product1->ProducePart(buildPara);


39:}


40: 


41:Product* ConcreteBuilder1::GetProduct()


42:{


43:return _product1;


44:}


45: 


46://ConcreteBuilder2


47:ConcreteBuilder2::ConcreteBuilder2()


48:{


49://std::cout << "ConcreteBuilder2..." << std::endl;


50:_product2 = new Product;


51:}


52:ConcreteBuilder2::~ConcreteBuilder2()


53:{


54://std::cout << "~ConcreteBuilder2..." << std::endl;


55:}


56://


57:void ConcreteBuilder2::BuildPartA(const std::string& buildPara)


58:{


59:_product2->ProducePart(buildPara);


60:}


61:void ConcreteBuilder2::BuildPartB(const std::string& buildPara)


62:{


63:_product2->ProducePart(buildPara);


64:}


65:Product* ConcreteBuilder2::GetProduct()


66:{


67:return _product2;


68:}


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://Product.cpp


2:#include "Product.h"


3:#include


4: 


5://


6:ProductPart::ProductPart(const std::string& part)


7::_part(new std::string(part))


8:{ }


9: 


10:ProductPart::~ProductPart()


11:{ 


12:if(_part)


13:{


14:delete _part;


15:_part = 0;


16:}


17:else


18:_part = 0;


19:}


20:std::string* ProductPart::getPart() const


21:{


22:return _part;


23:}


24://


25:Product::Product(){}


26:Product::~Product()


27:{


28://std::cout << "~Product" << std::endl;


29:partsVect::iterator iter;


30:for(iter = parts.begin(); iter != parts.end(); ++iter)


31:{


32:delete *iter;


33:*iter = 0;


34:}


35:}


36:void Product::ProducePart(const std::string& str)


37:{


38:parts.push_back(new ProductPart(str));


39:}


40:void Product::displayPart()


41:{


42:std::cout << "displayPart..." << std::endl;


43:partsVect::iterator iter;


44:for(iter = parts.begin(); iter != parts.end(); ++iter)


45:{


46:std::cout << *((*iter)->getPart()) << std::endl;


47:}


48:}


49: 


.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

1://test.cpp


2:#include "Builder.h"


3:#include"Product.h"


4:#include"Director.h"


5:#include


6: 


7:int main(int argc,char* argv[])


8:{


9:Product* p1;


10:ConcreteBuilder1* b1 = new ConcreteBuilder1;


11:Director* d1 = new Director(b1);


12:d1->Construct();


13:p1 = b1->GetProduct();


14:p1->displayPart();


15:


16:ConcreteBuilder2* b2 = new ConcreteBuilder2;


17:Product* p2;


18:if(d1->setBuilder(b2))


19:{


20:d1->Construct();


21:p2 = b2->GetProduct();


22:p2->displayPart();


23:}


24:else{


25:std::cout << "Can not create b2!" << std::endl;


26:}


27: 


28:delete d1;


29:d1 = 0;


30:delete p1;


31:p1 = 0;


32:if(p2)


33:{


34:delete p2;


35:p2 = 0;


36:}


37: 


38:return 0;


39:}



                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: