Initialization lists are an alternative technique for initializing an object's data members in a constructor. For instance, the constructor Show
can instead be written using an initialization list:
Both built-in types and objects can be initialized using initialization lists. Arrays (including C strings) can not be initialized using initialization lists. Initializing an object this way results in a constructor call. For example, if
a class called
Initialization Lists and Scope IssuesIf you have a data member of your class that has the same name as a parameter to your constructor, then the initialization list "does the right thing." For instance,
is roughly equivalent to
That is, the compiler knows which When to Use Initializer ListsUsing initialization lists to initialize data members in a constructor can be convenient if you don't need to do any error-checking on the constructor arguments. There are also several instances in C++ where the use of an initializer list to initialize a data member is actually required:
Constructor is a special non-static member function of a class that is used to initialize objects of its class type. In the definition of a constructor of a class, member initializer list specifies the initializers for direct and virtual base subobjects and non-static data members. ( Not to be confused with std::initializer_list ) Contents
[edit] SyntaxConstructors are declared using member function declarators of the following form:
Where class-name must name the current class (or current instantiation of a class template), or, when declared at namespace scope or in a friend declaration, it must be a qualified class name. The only specifiers allowed in the decl-specifier-seq of a constructor declaration are
friend, inline, The body of a
function definition of any constructor, before the opening brace of the compound statement, may include the member initializer list, whose syntax is the colon character
struct S { int n; S(int); // constructor declaration S() : n(7) {} // constructor definition. // ": n(7)" is the initializer list // ": n(7) {}" is the function body }; S::S(int x) : n{x} {} // constructor definition. ": n{x}" is the initializer list int main() { S s; // calls S::S() S s2(10); // calls S::S(int) } [edit] ExplanationConstructors have no names and cannot be called directly. They are invoked when
initialization takes place, and they are selected according to the rules of initialization. The constructors without Before the compound statement that forms the function body of the constructor begins executing, initialization of all direct bases, virtual bases, and non-static data members is finished. Member initializer list is the place where non-default initialization of these objects can be specified. For members that cannot be default-initialized, such as members of reference and const-qualified types, member initializers must be specified. The initializers where class-or-identifier names a virtual base class are ignored during execution of constructors of any class that is not the most derived class of the object that's being constructed. Names that appear in expression-list or brace-init-list are evaluated in scope of the constructor: class X { int a, b, i, j; public: const int& r; X(int i) : r(a) // initializes X::r to refer to X::a , b{i} // initializes X::b to the value of the parameter i , i(i) // initializes X::i to the value of the parameter i , j(this->i) // initializes X::j to the value of X::i { } }; Exceptions that are thrown from member initializers may be handled by function-try-block Member functions (including virtual member functions) can be called from member initializers, but the behavior is undefined if not all direct bases are initialized at that point. For virtual calls (if the bases are initialized), the same rules apply as the rules for the virtual calls from constructors and destructors: virtual member functions behave as if the dynamic type of *this is the class that's being constructed (dynamic dispatch does not propagate down the inheritance hierarchy) and virtual calls (but not static calls) to pure virtual member functions are undefined behavior.
[edit] Initialization orderThe order of member initializers in the list is irrelevant: the actual order of initialization is as follows: 1) If the constructor is for the most-derived class, virtual base classes are initialized in the order in which they appear in depth-first left-to-right traversal of the base class declarations (left-to-right refers to the appearance in base-specifier lists) 2) Then, direct base classes are initialized in left-to-right order as they appear in this class's base-specifier list 3) Then, non-static data members are initialized in order of declaration in the class definition. 4) Finally, the body of the constructor is executed (Note: if initialization order was controlled by the appearance in the member initializer lists of different constructors, then the destructor wouldn't be able to ensure that the order of destruction is the reverse of the order of construction) [edit] Examplestruct Class : public Base { unsigned char x; unsigned char y; Class ( int x ) : Base ( 123 ), // initialize base class x ( x ), // x (member) is initialized with x (parameter) y { 0 } // y initialized to 0 {} // empty compound statement Class ( double a ) : y ( a+1 ), x ( y ) // x will be initialized before y, its value here is indeterminate {} // base class constructor does not appear in the list, it is // default-initialized (not the same as if Base() were used, which is value-init) Class() try // function-try block begins before the function body, which includes init list : Base ( 789 ), x ( 0 ), y ( 0 ) { // ... } catch (...) { // exception occurred on initialization } }; [edit] Defect reportsThe following behavior-changing defect reports were applied retroactively to previously published C++ standards.
[edit] References
When using initializer lists in what order are member variables initialized?Const member variables must be initialized. A member initialization list can also be used to initialize members that are classes. When variable b is constructed, the B(int) constructor is called with value 5. Before the body of the constructor executes, m_a is initialized, calling the A(int) constructor with value 4.
What is constructor initialization list?Initializer List is used in initializing the data members of a class. The list of members to be initialized is indicated with constructor as a comma-separated list followed by a colon. Following is an example that uses the initializer list to initialize x and y of Point class.
What is a constructor initializer list and what are its uses?Constructor is a special non-static member function of a class that is used to initialize objects of its class type. In the definition of a constructor of a class, member initializer list specifies the initializers for direct and virtual bases and non-static data members.
Should my constructors use initialization lists or assignment?Conclusion: All other things being equal, your code will run faster if you use initialization lists rather than assignment.
|