In this specific case, is there a difference between using a member initializer list and assigning values in a constructor?

后端 未结 12 838
北恋
北恋 2020-11-22 08:16

Internally and about the generated code, is there a really difference between :

MyClass::MyClass(): _capacity(15), _data(NULL), _len(0)
{
}

相关标签:
12条回答
  • 2020-11-22 08:44

    The real difference boils down to how the gcc compiler generate machine code and lay down the memory. Explain:

    • (phase1) Before the init body (including the init list): the compiler allocate required memory for the class. The class is alive already!
    • (phase2) In the init body: since the memory is allocated, every assignment now indicates an operation on the already exiting/'initialized' variable.

    There are certainly other ways to handle const type members. But to ease their life, the gcc compiler writers decide to set up some rules

    1. const type members must be initialized before the init body.
    2. After phase1, any write operation only valid for non-constant members.
    0 讨论(0)
  • 2020-11-22 08:48

    I think this link http://www.cplusplus.com/forum/articles/17820/ gives an excellent explanation - especially for those new to C++.

    The reason why intialiser lists are more efficient is that within the constructor body, only assignments take place, not initialisation. So if you are dealing with a non-built-in type, the default constructor for that object has already been called before the body of the constructor has been entered. Inside the constructor body, you are assigning a value to that object.

    In effect, this is a call to the default constructor followed by a call to the copy-assignment operator. The initialiser list allows you to call the copy constructor directly, and this can sometimes be significantly faster (recall that the initialiser list is before the body of the constructor)

    0 讨论(0)
  • 2020-11-22 08:50

    You need to use initialization list to initialize constant members,references and base class

    When you need to initialize constant member, references and pass parameters to base class constructors, as mentioned in comments, you need to use initialization list.

    struct aa
    {
        int i;
        const int ci;       // constant member
    
        aa() : i(0) {} // will fail, constant member not initialized
    };
    
    struct aa
    {
        int i;
        const int ci;
    
        aa() : i(0) { ci = 3;} // will fail, ci is constant
    };
    
    struct aa
    {
        int i;
        const int ci;
    
        aa() : i(0), ci(3) {} // works
    };
    

    Example (non exhaustive) class/struct contains reference:

    struct bb {};
    
    struct aa
    {
        bb& rb;
        aa(bb& b ) : rb(b) {}
    };
    
    // usage:
    
    bb b;
    aa a(b);
    

    And example of initializing base class that requires a parameter (e.g. no default constructor):

    struct bb {};
    
    struct dd
    {
        char c;
        dd(char x) : c(x) {}
    };
    
    struct aa : dd
    {
        bb& rb;
        aa(bb& b ) : dd('a'), rb(b) {}
    };
    
    0 讨论(0)
  • 2020-11-22 08:50

    A big difference is that the assignment can initialize members of a parent class; the initializer only works on members declared at the current class scope.

    0 讨论(0)
  • 2020-11-22 08:50

    Depends on the types involved. The difference is similar between

    std::string a;
    a = "hai";
    

    and

    std::string a("hai");
    

    where the second form is initialization list- that is, it makes a difference if the type requires constructor arguments or is more efficient with constructor arguments.

    0 讨论(0)
  • 2020-11-22 08:53

    Here is a point that I did not see others refer to it:

    class temp{
    public:
       temp(int var);
    };
    

    The temp class does not have a default ctor. When we use it in another class as follow:

    class mainClass{
    public:
     mainClass(){}
    private:
      int a;
      temp obj;
    };
    

    the code will not compile, cause the compiler does not know how to initialize obj, cause it has just an explicit ctor which receives an int value, so we have to change the ctor as follow:

    mainClass(int sth):obj(sth){}
    

    So, it is not just about const and references!

    0 讨论(0)
提交回复
热议问题