设计模式循序渐进(7)创建模式 builder
一个使用Builder模式进行电脑组装的序列图:
模式解说:
将一个复杂对象的建造方法从其表现中分离出来,以便同样的建造方法可以建立不同的表现。
模式结构:
TAbstractBuilder:抽象建造者;定义一个抽象接口以创建产品对象的各个部分。
TConcreteBuilder:具体建造者;实现建造者接口,以创建及装配产品的各个部分。分步骤完成建造工作,在最后提供一个接口来返回该产品的实例。
TDirector:指导者;使用建造者接口来建造对象。
TProduct:产品;由建造者负责建造的复杂对象。
UML结构图:
Delphi代码:
模式解说:
将一个复杂对象的建造方法从其表现中分离出来,以便同样的建造方法可以建立不同的表现。
模式结构:
TAbstractBuilder:抽象建造者;定义一个抽象接口以创建产品对象的各个部分。
TConcreteBuilder:具体建造者;实现建造者接口,以创建及装配产品的各个部分。分步骤完成建造工作,在最后提供一个接口来返回该产品的实例。
TDirector:指导者;使用建造者接口来建造对象。
TProduct:产品;由建造者负责建造的复杂对象。
UML结构图:
Delphi代码:
unit uBuilder;
interface
type
IProduct = interface(IInterface)
end;
TProduct = class(TInterfacedObject, IProduct)
end;
TAbstractBuilder = class(TObject)
public
procedure BuildPart1; virtual; abstract;
procedure BuildPart2; virtual; abstract;
function GetProduct: IProduct; virtual; abstract;
end;
TConcreteBuilder = class(TAbstractBuilder)
public
procedure BuildPart1; override;
procedure BuildPart2; override;
function GetProduct: IProduct; override;
end;
TDirector = class(TObject)
private
FBuilder: TAbstractBuilder;
public
constructor Create(obj: TAbstractBuilder);
procedure Construct;
end;
implementation
{ TConcreteBuilder }
procedure TConcreteBuilder.BuildPart1;
begin
inherited;
Writeln('TConcreteBuilder.BuildPart1');
end;
procedure TConcreteBuilder.BuildPart2;
begin
inherited;
Writeln('TConcreteBuilder.BuildPart2');
end;
function TConcreteBuilder.GetProduct: IProduct;
begin
Writeln('TConcreteBuilder.GetProduct');
Result := nil;
end;
{ TDirector }
procedure TDirector.Construct;
begin
FBuilder.BuildPart1;
FBuilder.BuildPart2;
FBuilder.GetProduct;
end;
constructor TDirector.Create(obj: TAbstractBuilder);
begin
FBuilder := obj;
end;
end.
interface
type
IProduct = interface(IInterface)
end;
TProduct = class(TInterfacedObject, IProduct)
end;
TAbstractBuilder = class(TObject)
public
procedure BuildPart1; virtual; abstract;
procedure BuildPart2; virtual; abstract;
function GetProduct: IProduct; virtual; abstract;
end;
TConcreteBuilder = class(TAbstractBuilder)
public
procedure BuildPart1; override;
procedure BuildPart2; override;
function GetProduct: IProduct; override;
end;
TDirector = class(TObject)
private
FBuilder: TAbstractBuilder;
public
constructor Create(obj: TAbstractBuilder);
procedure Construct;
end;
implementation
{ TConcreteBuilder }
procedure TConcreteBuilder.BuildPart1;
begin
inherited;
Writeln('TConcreteBuilder.BuildPart1');
end;
procedure TConcreteBuilder.BuildPart2;
begin
inherited;
Writeln('TConcreteBuilder.BuildPart2');
end;
function TConcreteBuilder.GetProduct: IProduct;
begin
Writeln('TConcreteBuilder.GetProduct');
Result := nil;
end;
{ TDirector }
procedure TDirector.Construct;
begin
FBuilder.BuildPart1;
FBuilder.BuildPart2;
FBuilder.GetProduct;
end;
constructor TDirector.Create(obj: TAbstractBuilder);
begin
FBuilder := obj;
end;
end.
unit uClient;
interface
uses
uBuilder;
type
TClient = class(TObject)
public
procedure Process;
end;
implementation
{ TClient }
procedure TClient.Process;
var
Builder1: TAbstractBuilder;
Director1: TDirector;
begin
Builder1 := TConcreteBuilder.Create;
Director1 := TDirector.Create(Builder1);
Director1.Construct;
end;
end.
interface
uses
uBuilder;
type
TClient = class(TObject)
public
procedure Process;
end;
implementation
{ TClient }
procedure TClient.Process;
var
Builder1: TAbstractBuilder;
Director1: TDirector;
begin
Builder1 := TConcreteBuilder.Create;
Director1 := TDirector.Create(Builder1);
Director1.Construct;
end;
end.
program Project2;
{$APPTYPE CONSOLE}
uses
SysUtils,
uBuilder in 'uBuilder.pas',
uClient in 'uClient.pas';
var
Client: TClient;
begin
{ TODO -oUser -cConsole Main : Insert code here }
Client := TClient.Create;
Client.Process;
Client.Free;
Readln;
end.
{$APPTYPE CONSOLE}
uses
SysUtils,
uBuilder in 'uBuilder.pas',
uClient in 'uClient.pas';
var
Client: TClient;
begin
{ TODO -oUser -cConsole Main : Insert code here }
Client := TClient.Create;
Client.Process;
Client.Free;
Readln;
end.