1.简介
建造者模式是一种创建型设计模式,它允许你逐步构建一个复杂的对象,而无需让构造过程与表示层耦合。这样做的好处是你可以使用相同的构建过程创建不同的表示。
2.通俗讲解
假设我们要创建一个汽车工厂,需要生产不同类型的汽车,如轿车、SUV和卡车。每种类型的汽车都有其独特的配置选项,比如发动机类型、颜色等。我们希望有一个灵活的系统能够根据客户的需求来定制汽车的不同部分,同时保持代码的整洁性和可扩展性。
3.实战
3.1.代码
实现步骤:
- 定义产品接口 - 定义汽车的基本结构。
- 创建具体产品 - 创建具体的汽车类型。
- 定义建造者接口 - 规定组装各个部件的方法。
- 创建具体建造者 - 实现具体产品的组装逻辑。
- 使用Director类 - 控制具体的建造流程
C语言实现
car.h: 包含汽车结构体和建造者接口的声明。
#ifndef CAR_H
#define CAR_H
typedef struct Car {
char *type;
char *engine;
char *color;
} Car;
typedef struct Builder {
void (*set_type)(struct Builder *);
void (*set_engine)(struct Builder *, const char *);
void (*set_color)(struct Builder *, const char *);
} Builder;
#endif /* CAR_H */
car.c: 包含汽车结构体和建造者接口的实现。
#include "car.h"
#include <stdlib.h>
#include <string.h>
// 定义具体的建造者接口实现
void set_type(Builder *self) {
self->set_type(self);
}
void set_engine(Builder *self, const char *engine) {
self->set_engine(self, engine);
}
void set_color(Builder *self, const char *color) {
self->set_color(self, color);
}
sedan_builder.c: 包含SedanBuilder的具体实现。
#include "car.h"
#include <stdlib.h>
#include <string.h>
typedef struct SedanBuilder {
Builder base;
Car *car;
} SedanBuilder;
void sedan_builder_set_type(SedanBuilder *builder) {
builder->car->type = "Sedan";
}
void sedan_builder_set_engine(SedanBuilder *builder, const char *engine) {
builder->car->engine = strdup(engine);
}
void sedan_builder_set_color(SedanBuilder *builder, const char *color) {
builder->car->color = strdup(color);
}
SedanBuilder *sedan_builder_new() {
SedanBuilder *builder = malloc(sizeof(SedanBuilder));
builder->car = malloc(sizeof(Car));
builder->car->type = NULL;
builder->car->engine = NULL;
builder->car->color = NULL;
builder->base.set_type = &sedan_builder_set_type;
builder->base.set_engine = &sedan_builder_set_engine;
builder->base.set_color = &sedan_builder_set_color;
return builder;
}
void sedan_builder_free(SedanBuilder *builder) {
free(builder->car->engine);
free(builder->car->color);
free(builder->car);
free(builder);
}
director.c: 包含Director类的实现。
#include "car.h"
#include <stdlib.h>
#include <string.h>
typedef struct Director {
Builder *builder;
} Director;
Car *director_construct(Director *director) {
director->builder->set_type(director->builder);
director->builder->set_engine(director->builder, "V6");
director->builder->set_color(director->builder, "Red");
return director->builder->car;
}
main.c: 包含主函数。
#include "car.h"
#include <stdio.h>
int main() {
SedanBuilder *builder = sedan_builder_new();
Director director = { .builder = &builder->base };
Car *car = director_construct(&director);
printf("Car type: %s\n", car->type);
printf("Engine: %s\n", car->engine);
printf("Color: %s\n", car->color);
free(car->engine);
free(car->color);
free(car);
sedan_builder_free(builder);
return 0;
}
3.2.代码解析
- 我们首先定义了Car结构体作为我们的产品,然后定义了一个通用的Builder接口,该接口包含了设置汽车各部分的方法。
- SedanBuilder是一个具体的建造者,实现了上述接口方法,并提供了初始化和销毁方法。
- Director类用于控制具体的构建过程,这里简单地设置了汽车的类型、引擎和颜色。
- 在main函数中,我们实例化了一个SedanBuilder并使用Director来构建一辆车。
这就是一个简单的C语言实现的建造者模式的例子。这种模式使得我们可以方便地添加新的汽车类型或者修改现有类型的构建过程,而不会影响到现有的代码结构。
3.3.代码运行
Car type: Sedan
Engine: V6
Color: Red
3.4.结果分析
这表明我们的程序成功地使用建造者模式创建了一辆Sedan汽车,并且设置了它的类型为“Sedan”,引擎为“V6”,颜色为“Red”。这些信息是通过director_construct函数中的Director类来设置的,该类控制了具体的构建过程。
- 产品类 (Car):
Car结构体定义了汽车的基本属性,如类型、引擎和颜色。
每个属性都是动态分配的字符串指针,这样可以在构建过程中为它们赋值。 - 建造者接口 (Builder):
Builder接口定义了三个方法:set_type、set_engine 和 set_color。
这些方法用于设置Car结构体中的属性。 - 具体建造者 (SedanBuilder):
SedanBuilder实现了Builder接口,并为每个方法提供了具体的实现。
在sedan_builder_new函数中,我们为SedanBuilder分配内存,并将相应的接口方法指向具体的实现。 - Director类 (Director):
Director类负责控制具体的构建过程。
在director_construct函数中,我们调用Builder接口的方法来设置汽车的属性。 - 主函数 (main):
在main函数中,我们创建了一个SedanBuilder实例,并将其传递给Director类。
使用Director构建了一辆汽车,并打印了汽车的信息。
4.总结
建造者模式是一种非常实用的设计模式,尤其适用于需要创建具有复杂内部结构的对象的情况。在本例中,我们通过C语言实现了一个简单的汽车建造过程,展示了建造者模式如何帮助我们构建复杂对象的同时保持代码的整洁和可维护性。这种方法不仅适用于汽车这样的实体对象,也可以应用于任何需要逐步构建复杂对象的场景。