Initialization lists

Top  Previous  Next

What is translated > Types > Records, Classes, Interfaces > Class > Constructors > Initialization lists

 

In Delphi member variables like other variables too are initialized automatically with default values. Because this is not the case in C++ Delphi2C++ has to do these initializations explicitly, like in the following example:

 

. Delphi source                            C++ translation

 

 

  Base = class                             class Base: public System::TObject {  

  public                                     friend class Derived;               

    constructor Create(arg : Integer);       public:                             

    destructor Destroy;                      __fastcall Base( int arg );         

  private                                    __fastcall ~Base( );                

    FList : TList;                           private:                            

    FI : Integer;                            TList* FList;  

    FTimeOut: Longint;                       int FI;

  end;                                       int FTimeOut;                             

                                             public: inline __fastcall Base () {} <- dangerous

                                           };                                    

 

 

  constructor Base.Create(arg : Integer);  __fastcall Base::Base( int arg )

  begin                                     : FI(0),              

  end;                                        FList(NULL),        

                                              FTimeOut(0)         

                                           {                      

                                           } 

 

If the members are initialized explicitly in Delphi, Delphi2Cpp tries to find the according statements and puts them into the initialization list of the class constructor:

 

 

constructor Base.Create(arg : Integer);    __fastcall Base::Base( int arg )

begin                                       : FI(arg),                     

  FList := TList.Create;                      FList(new TList),            

  FI := arg;                                  FTimeOut(0)                  

  if arg <> $00 then                       {                               

    FTimeOut := arg                          if ( arg != 0x00 )            

  else                                         FTimeOut = arg;             

   FTimeOut := DefaultTimeout;               else                          

end;                                           FTimeOut = DefaultTimeout;

                                           }                 

 

The use of initialization lists is more efficient in C++ than to initialize the variables in the body of the constructor. But sometimes there is a problem with this method. For example, the initialization of the member FTimeOut depends of the value of the arg parameter. As shown in the next example Delphi2Cpp tries to take care about such cases. But Delphi2Cpp cannot find all such hidden dependencies, as in the following example:

 

 

constructor Derived.Create;                __fastcall Derived::Derived( )   

var                                         : inherited( i ),               

  i : Integer;                                FB(false)                     

begin                                      {                                

  i := SomeFunction;                         int i = 0;                     

  inherited Create(i);                       i = SomeFunction;              

end;                                       }                                

 

 

In such cases constructors have to be corrected manually like:

 

__fastcall Derived::Derived( )

 : inheritd( SomeFunction() )

{

}

 

 

Unfortunately, there is another problem with the order of the initializations. in C++ the order in the initializer list is ignored. Member variables are always initialized in the order they appear in the class declaration. In the following example:

 

 

TInit = class(TObject)

  FName1, FName2, FName4, FName3 : String;

  constructor Create(Name1, Name2, Name3 : String);

end;

 

implementation

 

constructor TInit.Create(Name1, Name2, Name3 : String);

begin

  FName1 := Name1;

  FName2 := Name2;

  FName3 := Name3;

  FName4 := FName3;

end;

                                           

a strict initialization of the member variables in the order in which they are declared would lead to: 

 

 

__fastcall TInit::TInit( String Name1, String Name2, String Name3 )

 : FName1(Name1),

   FName2(Name2),

   FName4(FName3),

   FName3(Name3)

{

}

 

Obviously, this is not correct. Therefore Delphi2Cpp uses the following strategy: as long as the initialization statements in the constructor are in the order of the declarations, they are shifted into the initializer list. For all other member variables follows initialization code in the body of the constructor.

 

 

__fastcall TInit::TInit( String Name1, String Name2, String Name3 )

 : FName1(Name1),

   FName2(Name2),

   FName3(Name3)

{

  FName4 = FName3;

}

 

 

                                                                                                           

                                                                                                            

 

 

 



This page belongs to the Delphi2Cpp Documentation

Delphi2Cpp home  Content