Personally if I have primitive variables that I need to initialise in a specific order, I'm not going to rely on the class definition order to do it, and that means good old fashioned assignment with the = operator.
And if I need bananas, I'm going to eat good old fashioned apples!
assignment != initialization 
By the time your assignment is actually reached, your variables will have already been default-initialized (though it'd probably be optimized out* if the variable isn't accessed before your assignment).
*Which is less a guarantee than the standard-guaranteed initialization order.
I emboldened the key part in the above quote -- primitive types aren't default initialized, so when it comes to assigning their default values, then the choice of using the initializer list, or assignment in the constructor body is
purely a choice of style. They both generate the same results (
unless of course, another item in the initializer list is initialized using the value of a primitive member), so saying one is more correct than the other is nothing more than a style war.
Why wouldn't you rely on the standardized initialization order?
I've got a lot of classes that look like:
class Foo
{
Bar bar;
Baz baz;
public: Foo() : bar(42), baz(bar) {}
};, which works fine -- bar is initialized before being passed into baz's constructor. As mentioned earlier, if the initializer list and the variable declaration orders are mismatched, then your compiler should warn you (
in this case, a mismatch could cause baz to be passed an uninitialized variable). So far so good.
However, on every shipping game I've worked on, there comes a phase of panic during the final crunch period where the worst-case memory usage of the game is too high, and the QA department is able to produce out-of-memory errors (
on consoles). One of the emergency measures that often happens at this point is some poor sod gets given the task of eliminated any unnecessary padding from everyone's data structures, which usually involves going through every class/struct and sorting all member declarations by their sizes (
e.g. pushing all chars to the bottom of the class/struct).
Due to the C++ decision to enforce initialization in order of declaration this now causes a conflict -- the initialization list is written in the order that makes logical sense (
e.g. so that bar is constructed before being passed to baz) and the declarations are ordered in a way to minimize padding, but C++ wants them both to be the same.
If said poor sod is to complete their assignment, they are now forced to depart from accepted C++ style and start writing horrible looking constructors to trick C++ into satisfying these two conflicting requirements.
I don't know the background behind why the C++ standardization people decided to enforce initialization in declaration order, instead of initialization in initialization order, but IMHO it was a mistake to make that decisiion. Initialization order is bound by logical constraints, but declaration order should only be a concern for memory layout, and should be decoupled from the concern of initialization.
N.B. more modern languages have gotten this right -- e.g. C# declaration order isn't even followed unless you manually specify that you require a certain layout, by default the compiler can rearrange your declarations to the most efficient layout, and allow you to initialize your members in their logical order.
Edited by Hodgman, 06 October 2012 - 06:29 AM.