从另一个调用一个重载的构造函数是否有意义?

时间:2014-01-30 16:17:08

标签: delphi constructor overloading

如果我有两个重载的构造函数,一个没有,一个带参数:

constructor Create; overload;
constructor Create(Param: TObject); overload;

如果我希望第一个代码运行,那么在第二个代码中调用它是否有意义?并继承首先调用父构造函数?

constructor TMyType.Create(Param: TObject);
begin
  inherited Create;
  Create;
  FParam := Param;
end;

谢谢!

2 个答案:

答案 0 :(得分:0)

  

如果我希望第一个代码运行,是否有意义在第二个中继续调用它以便首先调用父构造函数?

没有。因为你的第一个构造函数应该自己调用继承的构造函数,所以最后继承的构造函数会被调用两次,这很可能是不期望的。

否则,如果你的无参数TMyType.Create()没有调用继承的,那么它几乎不是一个合适的构造函数,应该被删除。

所以正确的方法就是这样:

constructor TMyType.Create(Param: TObject); overload;
begin
  Create();
  FParam := Param;
end;

constructor TMyType.Create();  overload;
begin
  inherited Create(); // for both constructors

  ...some common code
end;

然而在Delphi中还有另一种可能性。

constructor Create; overload;
constructor Create(Param: TObject); overload;
procedure AfterConstruction; override;


constructor TMyType.Create(Param: TObject); 
begin
  inherited Create(); 

  FParam := Param;
end;

constructor TMyType.Create();
begin
  inherited ; 

 ... maybe some extra code
end;

procedure TMyType.AfterConstruction();
begin
    inherited;

  ...some common code
end;

请注意区别,何时执行“公共代码”以及何时执行“FParam:= Param;”

在第一种方式中,流程就像

  • 创建(Param)
  • ..创建()
  • ....继承Create()
  • .... 通用代码
  • .. FParam:= Param;
  • AfterConstruction(空)

在第二个序列中会有所不同

  • 创建(参数)或创建()
  • .. Inherited Create()
  • .. FParam:= Param;
  • AfterConstruction
  • .. Common Code

正如您所看到的,正在执行的那些块的顺序被颠倒了。


但是,您可能根本不需要多个构造函数?

constructor TMyType.Create(const Param: TObject = nil); 
begin
  inherited; 

 ... Some code

  FParam := Param;
end;

答案 1 :(得分:-2)

是的,您的代码非常有意义,构造函数的调用完全符合您的预期。

Delphi对象模型支持调用继承构造函数的构造函数和不调用继承构造函数的构造函数。

如果你不确定试试这个:

program Project5;

{$APPTYPE CONSOLE}

uses
  SysUtils;

type
  TMyBase = class
    constructor Create;
  end;

  TMyType = class(TMyBase)
    constructor Create; overload;
    constructor Create(Param: TObject); overload;
  end;

constructor TMyBase.Create;
begin
  Writeln('TMyBase.Create');
end;

constructor TMyType.Create;
begin
  Writeln('TMyType.Create');
end;

constructor TMyType.Create(Param: TObject);
begin
  inherited Create;
  Create;
  Writeln('TMyType.Create(Param)');
end;

begin
  TMyType.Create(TObject.Create);
  Readln;
end.