The C++ standard does guarantee an order for initialization lists (ISO C++ Standard 12.6.2/5):
...nonstatic data members shall be
initialized in the order they were
declared in the class definition
(again regardless of the order of the
mem-initializers).
(See Wyatt Anderson's answer for more information.)
Example:
class Foo
{
public:
Foo();
private:
A a;
B b;
C c;
};
Foo::Foo() : b(), a(), c()
{
// a is initialized first, then b, then c - NOT b, a, then c!
}
However, you can't initialize a variable twice - what you have won't compile.
class X //() what's with the pair of parentheses you have in your code snippet?
{
public:
X();
private:
X_Implementation* impl_;
};
X::X() :
impl_(Allocate(sizeof(X_Implementation))),
// It is not allowed to initialize a data member twice!
impl_(Construct<X_Implementation>(impl_))
{
}
Instead, just put the extra work into the constructor:
X::X() : impl_(Allocate(sizeof(X_Implementation)))
{
impl_ = Construct<X_Implementation>(impl_);
}
There may be exception safety issues with the above code, but without knowing what Allocate()
or Construct()
actually does I'm not able to tell. I can tell you that it's best to separate allocation and construction into their own classes if you do that, using the Resource Acquisition Is Initialization (RAII) idiom:
class XBase
{
protected:
XBase() : impl_(Allocate(sizeof(X_Implementation)))
{
}
~XBase()
{
if(impl_ != 0) { Deallocate(impl_); } // Or something like this
}
X_Implementation* impl_;
};
class X : private XBase // XBase is an implementation detail
{
public:
X()
{
impl_ = Construct<X_Implementation>(impl_);
}
~X()
{
Destruct<X_Implementation>(impl_); // Or something like this
}
};
This way, if Construct()
throws an exception, you won't leak memory since the base class destructor will be called which will deallocate the memory pointed by impl_
. This is important because if the exception is not caught and leaves the constructor, its matching destructor will not be called. See Bjarne Stroustrup's paper on exception safety: http://www2.research.att.com/~bs/except.pdf