TITLE: Initialization order of members ............................................................................ PROBLEM: Klamer Schutte (klamer@mi.el.utwente.nl), 11 Jun 92 #include class A { int a, b; static int c; public: A() : b(c), a(c++) { } void print() { cout << a << ' ' << b << '\n'; } }; int A::c = 0; main() { A a; a.print(); } Sun C++ 2.1 gives as result 0 1 when gcc 2.2.1 gives 0 0 Is one of the compilers wrong here? If so, which? Or is this undefined by C++? ............................................................................ RESPONSE: Patrick Smith (uunet.ca!frumious!pat), 11 Jun 92 I think the problem posed here is subtler than it appears at first sight. A couple people responded with references to page 292 of the ARM, which states that members are initialized in the order of declaration, and concluded that the correct output is 0 1. But the important point in this program is not the order of initialization - it's the order in which the arguments to the initializers are evaluated. For example, is it legal to do the computations in this order? 1) Evaluate c 2) Evaluate c++ 3) Initialize a.a with the result of step 2 4) Initialize a.b with the result of step 1 This obeys the restriction from page 292 of the ARM: a.a is initialized before a.b. But the output of the program would be 0 0 (as produced by gcc). In a quick search of the ARM, I didn't find anything that would prohibit this behaviour. I suspect, however, that there is a fair bit of code which assumes that this type of behaviour won't happen. Consider, for example, class X { int a; int b; public: X( int i ) : a( i * i ), b( a * 17 ) {} }; What do other people think? ............................................................................ RESPONSE: Jerry Schwarz (jss@lucid.com), 11 Jun 92 The ARM does not address this issue. Indeed, it does not address any of the issues that are addressed by the notion of "sequence point" that was introduced by the C standard. There have been discussions of this issue by X3J16 members and the concensus is that there should be "sequence points" before each construction/initialization occurs. What this means is that only legal order would be 1. Evalauate c++, including it's side effect 2. Construct a with result of 1 3. Evaluate c 4. Construct b with the result of 2 However, X3J16 as a whole has not yet officially adopted any position with regard to sequence points in general or this matter in particular, so no definitive answer is possible.