Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

When an array is created by a subexpression, what happens with the temporaries therein?

I was reading these two paragraphs of the FDIS (12.2p{4,5}):

There are two contexts in which temporaries are destroyed at a different point than the end of the full-expression. The first context is when a default constructor is called to initialize an element of an array. If the constructor has one or more default arguments, the destruction of every temporary created in a default argument is sequenced before the construction of the next array element, if any.

and

The second context is when a reference is bound to a temporary. The temporary to which the reference is bound or the temporary that is the complete object of a subobject to which the reference is bound persists for the lifetime of the reference except: [...]

  • A temporary bound to a reference parameter in a function call (5.2.2) persists until the completion of the full-expression containing the call.

These two two seem to contradict for the following case

struct A {
  A() { std::cout << "C" << std::endl; }
  ~A() { std::cout << "D" << std::endl; }
};

struct B {
  B(A const& a = A()) { }
};

typedef B array[2];

int main() {
  array{};
}

Will this output CDCD as required by the first context, or will this output CCDD as required by the second context? GCC seems to follow the second context description and outputs CCDD. Have I overlooked something important?


EDIT: I don't think it needs C++0x. This new-expression is affected too by my question:

new array(); /* CDCD or CCDD ?? */

In this case though, GCC follows the first context, and outputs CDCD.

like image 363
Johannes Schaub - litb Avatar asked Jun 11 '11 11:06

Johannes Schaub - litb


1 Answers

I don't think there's a contradiction.

5.2.2 clearly says what a function call is. A function call is a postfix expression followed by parentheses containing a possibly empty, comma-separated list of expressions which constitute the arguments to the function.

There doesn't seem to be a function call to B::B(A const&) anywhere in your program, so I don't see how the second passage applies.

EDIT the above is probably incorrect, given 1.9p10 etc.

like image 198
n. 1.8e9-where's-my-share m. Avatar answered Oct 05 '22 01:10

n. 1.8e9-where's-my-share m.