4

Source of question:

The only failing case is passing parameters by non-const reference, since temporary variable couldn't be bound to it.

void DrawLine(const Vector& v1, const Vector& v2);

If the object is temporary, why would making the reference const have any effect on the lifetime of the temporary object?

I guess I also don't fully understand the scope of existence for temporary objects created in an argument.

Bob
  • 4,576
  • 7
  • 39
  • 107
  • @MarcGlisse there must have been a reason. I'm sure they didn't just flip a coin. – Bob Mar 06 '18 at 23:04
  • 3
    This may just resolve down to "It's dang useful." but I'm going to keep an eye on this to see what pops up. – user4581301 Mar 06 '18 at 23:06
  • Your question is confusing. Are you asking about why a const reference bound to temporary extends it's lifetime (as in your body)? Or are you asking about why you can bind a const reference to a temporary and pass it to function this way (as your title and code snippet suggests)? Note, in your code there is no life-time extension. – SergeyA Mar 06 '18 at 23:11
  • @SergeyA those two sound very related, almost the same. What clarifications are you suggesting? – Bob Mar 06 '18 at 23:14
  • No, they are two different questions. You could have had an option of binding a const reference to a temporary, but without lifetime extension - and it would still allow passing arguments to functions this way. – SergeyA Mar 06 '18 at 23:16
  • @SergeyA if its lifetime is not extended then it's not possible to bind anything so how can you pass along what's expired? – Bob Mar 06 '18 at 23:19
  • 1
    [Why reference cannot capture temporary](https://stackoverflow.com/a/25025717/597607) – Bo Persson Mar 06 '18 at 23:43
  • 2
    There's no lifetime extension if you call `Drawline(Vector{}, Vector{});`. The lifetime of both temporary `Vector`s end at the end of the full expression, so you can use them within the function. On the other hand, if you write `auto const& v = Vector{};`, the lifetime of the temporary is extended to match that of `v`. So which of these are you asking about? – Praetorian Mar 07 '18 at 02:02

1 Answers1

6

If the object is temporary, why would making the reference const have any effect on the lifetime of the temporary object?

In the present context, the issue is not the lifetime of the object but whether you can modify it.

Say you make a call.

foo(10);

The object that holds the value 10 in the call should not be modified by the function. If the interface of foo is:

void foo(int& ref);

it's fair to implement foo as:

void foo(int& ref)
{
   ref = 20;
}

That would be a problem given the call foo(10). It won't be a problem if foo uses a const&.

void foo(int const& ref)
{
   ref = 20; // Not allowed.
}

From C++11 Standard, Temporary Objects/1

Temporaries of class type are created in various contexts: binding a reference to a prvalue ([dcl.init.ref]), returning a prvalue ([stmt.return]), a conversion that creates a prvalue, ...

and from C++11 Standard, References/5.2:

-- Otherwise, the reference shall be an lvalue reference to a non-volatile const type (i.e., cv1 shall be const), or the reference shall be an rvalue reference.

A temporary can only bind to a reference to a prvalue. The type of such a reference must be a const qualified lvalue reference or a rvalue references.

MS Visual Studio compilers have allowed binding of non-const references to temporary objects but it is not sanctioned by the standard.

R Sahu
  • 204,454
  • 14
  • 159
  • 270