NOT the most important const .. but what is it?

This outputs F~ , but I was expecting ~F

 #include <iostream> struct Foo { int _x; operator const int & () const {return _x;} ~ Foo () {std :: cout << "~";} }; void foo (const int &) { std :: cout << "F"; } int main () { foo (Foo ()); } 

I built it as a counterexample to show that the most important const is an exception, not a rule. It is usually written as

when a const reference refers to a temporary one, then the lifetime of this temporary object extends to the lifetime of the link

I tried to illustrate this, although Foo() is temporary, the _x reference returned by the conversion operator is not, and that the above code is unsafe.

But the result, it seems, proves that the example is safe, the lifetime of temporary Foo() extends due to the existence of a const reference to one of its members.

Is it correct? Where does the standard indicate this?

+7
source share
4 answers

The general rule regarding time tenses is that their life ends when they are fully expressed as part of the ends (informally when you reach ; ).

12.2 Temporary objects

3 / [...] Temporary objects are destroyed as the last step in evaluating the full expression (1.9), which (lexically) contains the point at which they were created. This is true even if this estimate ends with an exception. The calculation of the values ​​and side effects of the destruction of a temporary object are associated only with the full expression, and not with any specific subexpression.

+6
source

This is because the temporary survives the entire time the function is called. When you do foo (Foo ()); here what happens:

  • temporary Foo is executed then
  • operator const int& is called in temporary
  • foo() is called by F
  • once foo() returns a temporary Foo destroyed, and this outputs ~
+1
source

There is no magic here. All function arguments are within the scope of the caller's call, including temporary ones. Temporary Foo() is created within the calling area of ​​the caller and destroyed at the end of the line.

So any function Foo() is executed before its arguments in main() are destroyed.

+1
source

But your Foo instance will always live here until the semicolon completes the statement in which it was created. Passing a member reference into a function call did not change this.

Try:

 int const &ref = Foo(); foo(ref); 

against

 Foo const &ref = Foo(); // or function returning temp foo(ref); 
0
source

All Articles