建造者模式(c++实现)

建造者模式

模式定义

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

模式动机

  • 如果我们用了建造者模式,那么用户就只需指定需要建造的类型就可以得到它们,而具体建造的过程和细节就不需要知道了。
  • 主要是用于创建一些复杂的对象,这些对象内部构建间的建造顺序通常是稳定的,但对象内部的构建通常面临着复杂的变化。
  • 建造者模式是在当创建复杂对象的算法应该独立于该对象的组成部分以及它们的装配方式时适用的模式。

UML类图

说明:

  • Builder:是为创建一个Product对象的各个部件指定的抽象接口。
  • ConcreteBuilder:是具体的建造者,实现Builder接口,构造和装配各个部件。
  • Product:具体的产品角色。
  • Director:指挥者,它是构建一个使用Builder接口的对象。

源码实现

  • builder.h
#include "product.h"

class Builder
{
public:
    Builder();
    virtual ~Builder(){}
    virtual void AddPartA();
    virtual void AddPartB();

    Product* GetProduct();
protected:
    Product*        m_Product;
};
  • builder.cpp
#include <iostream>
#include "builder.h"

Builder::Builder()
{
    m_Product = new Product();
}

void Builder::AddPartA()
{
    m_Product->AddPart("PartA");
}

void Builder::AddPartB()
{
    m_Product->AddPart("PartB");
}

Product* Builder::GetProduct()
{
    if(m_Product->PartsCount() > 0)
        return m_Product;
    else
        std::cout << "产品还未组装好" << std::endl;
}
  • concretebuilder1.h
#include "builder.h"

class ConcreteBuilder1 : public Builder
{
public:
    ConcreteBuilder1();
    void AddPartA() override;
    void AddPartB() override;
};
  • concretebuilder1.cpp
#include "concretebuilder1.h"

ConcreteBuilder1::ConcreteBuilder1()
{

}

void ConcreteBuilder1::AddPartA()
{
    m_Product->AddPart("Part1");
}

void ConcreteBuilder1::AddPartB()
{
    m_Product->AddPart("Part2");
}
  • director.h
#include "builder.h"

class Director
{
public:
    Director();
    void Construct(Builder* builder);
};
  • director.cpp
#include "director.h"

Director::Director()
{

}

void Director::Construct(Builder *builder)
{
    builder->AddPartA();
    builder->AddPartB();
}
  • product.h
#include <list>
#include <string>

class Product
{
public:
    Product();
    void AddPart(std::string part);
    void Show();

    int PartsCount();
private:
    std::list<std::string>      m_Parts;
};
  • product.cpp
#include "product.h"
#include <iostream>

Product::Product()
{

}

void Product::AddPart(std::string part)
{
    m_Parts.push_back(part);
}

void Product::Show()
{
    std::cout << "组成部分:" << std::endl;
    for(auto part : m_Parts)
    {
        std::cout << part << std::endl;
    }
}

int Product::PartsCount()
{
    return m_Parts.size();
}
  • main.cpp
#include <iostream>
#include <memory>
#include "concretebuilder1.h"
#include "concretebuilder2.h"
#include "director.h"
using namespace std;

int main()
{
    std::shared_ptr<Builder> builder1 = std::make_shared<ConcreteBuilder1>();
    std::shared_ptr<Builder> builder2 = std::make_shared<ConcreteBuilder2>();

    Director director;
    director.Construct(builder1.get());
    Product* product1 = builder1->GetProduct();
    product1->Show();

    director.Construct(builder2.get());
    Product* product2 = builder2->GetProduct();
    product2->Show();


    return 0;
}
  • 运行结果

组成部分:

Part1

Part2

组成部分:

PartX

PartY

优点

建造者模式的优点

  • 使得建造代码与表示代码分离,由于建造者隐藏了该产品是如何组装的,所以若需要改变一个产品的内部表示,只需要再定义一个具体的建造者就可以了。

缺点

模式的缺点

posted @ 2020-07-15 18:20  鬼谷子com  阅读(913)  评论(0编辑  收藏  举报