解决的问题
生成器模式(Builder Pattern)主要解决复杂对象的构建问题。当一个对象的创建过程非常复杂,涉及多个步骤和多个部件时,使用生成器模式可以将对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。
适用场景
- 复杂对象的构建:当对象的构建过程非常复杂,涉及多个步骤和多个部件时。
- 不同的构建过程:当需要不同的表示时,可以使用相同的构建过程。
- 逐步构建:当对象的构建过程可以逐步进行时。
模式的参与者角色
- Builder(生成器接口):定义构建产品的各个部件的抽象接口。
- ConcreteBuilder(具体生成器):实现
Builder
接口,负责构建产品的各个部件。 - Product(产品):表示正在构建的复杂对象。
- Director(指导者):使用
Builder
接口来构建产品。
以生产汽车为例的生成器模式示例代码
#include <iostream>
#include <string>
// 产品类:汽车
class Car {
public:
void setBody(const std::string& body) { body_ = body; }
void setEngine(const std::string& engine) { engine_ = engine; }
void setWheels(const std::string& wheels) { wheels_ = wheels; }
void setInterior(const std::string& interior) { interior_ = interior; }
void show() const {
std::cout << "Car Configuration: " << std::endl;
std::cout << "Body: " << body_ << std::endl;
std::cout << "Engine: " << engine_ << std::endl;
std::cout << "Wheels: " << wheels_ << std::endl;
std::cout << "Interior: " << interior_ << std::endl;
}
private:
std::string body_;
std::string engine_;
std::string wheels_;
std::string interior_;
};
// 抽象生成器接口
class CarBuilder {
public:
virtual ~CarBuilder() {}
virtual void buildBody() = 0;
virtual void buildEngine() = 0;
virtual void buildWheels() = 0;
virtual void buildInterior() = 0;
virtual Car* getCar() = 0;
};
// 具体生成器:SUV 汽车
class SUVBuilder : public CarBuilder {
public:
SUVBuilder() { car_ = new Car(); }
~SUVBuilder() { delete car_; }
void buildBody() override { car_->setBody("SUV Body"); }
void buildEngine() override { car_->setEngine("SUV Engine"); }
void buildWheels() override { car_->setWheels("SUV Wheels"); }
void buildInterior() override { car_->setInterior("SUV Interior"); }
Car* getCar() override { return car_; }
private:
Car* car_;
};
// 具体生成器:Sedan 汽车
class SedanBuilder : public CarBuilder {
public:
SedanBuilder() { car_ = new Car(); }
~SedanBuilder() { delete car_; }
void buildBody() override { car_->setBody("Sedan Body"); }
void buildEngine() override { car_->setEngine("Sedan Engine"); }
void buildWheels() override { car_->setWheels("Sedan Wheels"); }
void buildInterior() override { car_->setInterior("Sedan Interior"); }
Car* getCar() override { return car_; }
private:
Car* car_;
};
// 指导者
class Director {
public:
void setBuilder(CarBuilder* builder) { builder_ = builder; }
Car* constructCar() {
builder_->buildBody();
builder_->buildEngine();
builder_->buildWheels();
builder_->buildInterior();
return builder_->getCar();
}
private:
CarBuilder* builder_;
};
// 客户端代码
int main() {
Director director;
// 创建 SUV
std::cout << "Building SUV..." << std::endl;
SUVBuilder suvBuilder;
director.setBuilder(&suvBuilder);
Car* suv = director.constructCar();
suv->show();
delete suv;
// 创建 Sedan
std::cout << "\nBuilding Sedan..." << std::endl;
SedanBuilder sedanBuilder;
director.setBuilder(&sedanBuilder);
Car* sedan = director.constructCar();
sedan->show();
delete sedan;
return 0;
}
代码说明
- Car 类表示正在构建的汽车产品,包含汽车的各个部件。
- CarBuilder 是一个抽象生成器接口,定义了构建汽车各个部件的方法和一个获取最终产品的接口。
- SUVBuilder 和 SedanBuilder 是具体生成器类,分别实现了
CarBuilder
接口,用于构建 SUV 和 Sedan 汽车。 - Director 类负责使用
CarBuilder
接口来构建汽车。它通过调用生成器的各个构建方法来逐步构建汽车。 - Client 在
main
函数中使用Director
和具体生成器来构建不同类型的汽车,并展示汽车配置。
总结
生成器模式通过将复杂对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。在需要逐步构建复杂对象或需要不同表示的场景中,生成器模式非常有用。
模板方法(Template Method)模式与生成器(Builder)模式
形式相似点
- 抽象类与具体类:两种模式都涉及抽象类(或接口)和具体实现类。
- 分步构建:都需要分步骤构建复杂对象或执行算法。
目的的不同点
- 模板方法模式:定义一个算法的框架,允许子类在不改变算法结构的情况下重新定义算法的某些步骤。目的是为了代码复用和算法的一致性。
- 生成器模式:将复杂对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。目的是为了构建复杂对象时的灵活性和可扩展性。
模板方法模式的代码示例
#include <iostream>
#include <string>
// 抽象类,定义模板方法
class AbstractClass {
public:
// 模板方法
void templateMethod() {
step1();
step2();
step3();
}
protected:
virtual void step1() = 0;
virtual void step2() = 0;
virtual void step3() = 0;
};
// 具体类1
class ConcreteClass1 : public AbstractClass {
protected:
void step1() override {
std::cout << "ConcreteClass1: Step 1" << std::endl;
}
void step2() override {
std::cout << "ConcreteClass1: Step 2" << std::endl;
}
void step3() override {
std::cout << "ConcreteClass1: Step 3" << std::endl;
}
};
// 具体类2
class ConcreteClass2 : public AbstractClass {
protected:
void step1() override {
std::cout << "ConcreteClass2: Step 1" << std::endl;
}
void step2() override {
std::cout << "ConcreteClass2: Step 2" << std::endl;
}
void step3() override {
std::cout << "ConcreteClass2: Step 3" << std::endl;
}
};
// 客户端代码
int main() {
AbstractClass* class1 = new ConcreteClass1();
class1->templateMethod();
delete class1;
std::cout << std::endl;
AbstractClass* class2 = new ConcreteClass2();
class2->templateMethod();
delete class2;
return 0;
}
生成器模式的代码示例
#include <iostream>
#include <string>
// 产品类
class Product {
public:
void setPartA(const std::string& partA) { partA_ = partA; }
void setPartB(const std::string& partB) { partB_ = partB; }
void setPartC(const std::string& partC) { partC_ = partC; }
void show() const {
std::cout << "Product parts: " << partA_ << ", " << partB_ << ", " << partC_ << std::endl;
}
private:
std::string partA_;
std::string partB_;
std::string partC_;
};
// 抽象生成器接口
class Builder {
public:
virtual ~Builder() {}
virtual void buildPartA() = 0;
virtual void buildPartB() = 0;
virtual void buildPartC() = 0;
virtual Product* getProduct() = 0;
};
// 具体生成器
class ConcreteBuilder : public Builder {
public:
ConcreteBuilder() { product_ = new Product(); }
~ConcreteBuilder() { delete product_; }
void buildPartA() override { product_->setPartA("PartA"); }
void buildPartB() override { product_->setPartB("PartB"); }
void buildPartC() override { product_->setPartC("PartC"); }
Product* getProduct() override { return product_; }
private:
Product* product_;
};
// 指导者
class Director {
public:
void setBuilder(Builder* builder) { builder_ = builder; }
Product* constructProduct() {
builder_->buildPartA();
builder_->buildPartB();
builder_->buildPartC();
return builder_->getProduct();
}
private:
Builder* builder_;
};
// 客户端代码
int main() {
Director director;
// 创建具体生成器
ConcreteBuilder builder;
director.setBuilder(&builder);
// 构建产品
Product* product = director.constructProduct();
product->show();
delete product;
return 0;
}
代码说明
模板方法示例
- AbstractClass:定义了一个模板方法
templateMethod()
,其中包含了三个抽象步骤step1()
,step2()
,step3()
。 - ConcreteClass1 和 ConcreteClass2:具体子类,分别实现了抽象步骤,但模板方法的结构保持不变。
- 客户端代码:通过创建
ConcreteClass1
和ConcreteClass2
的对象,调用templateMethod()
方法来执行算法,子类可以在不改变算法结构的情况下重新定义算法的某些步骤。
生成器模式示例
- Product:表示正在构建的复杂对象。
- Builder:抽象生成器接口,定义了构建产品的各个部件的方法和一个获取最终产品的接口。
- ConcreteBuilder:具体生成器类,实现了
Builder
接口,负责构建产品的各个部件。 - Director:指导者类,使用
Builder
接口来构建产品。通过调用生成器的各个构建方法来逐步构建产品。 - 客户端代码:通过
Director
和ConcreteBuilder
来构建产品,并展示产品配置。
总结
- 模板方法模式:目的是为了代码复用和算法的一致性,通过定义算法的框架,允许子类在不改变算法结构的情况下重新定义算法的某些步骤。
- 生成器模式:目的是为了构建复杂对象时的灵活性和可扩展性,通过将复杂对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。