outmind
outmind

Reputation: 829

Why operator= returns reference not const reference

The original question is related to overloading operator= and I like to share my findings as it was nontrivial for me to find them. I cannot imagine reasonable example to use (a=b) as lvalue. With the help of IRC and google I've found the next article: http://msdn.microsoft.com/en-us/magazine/cc301415.aspx

it provides two examples.

  (a=b)=c

  f(T& );
  f(a=b)

but both a bit not good, and I believe that it is bad practice. The second one give me the same feeling. Could you provide more good examples why it should be non constant?

Upvotes: 6

Views: 2311

Answers (6)

Jerry Coffin
Jerry Coffin

Reputation: 490168

Andrew Koenig wrote a post about this a long time ago. A lot of it comes down to doing what people expect under slight unusual circumstances. The example he gives is that in C, return x=y; always means the same thing as x=y; return x;. In C++, if you return essentially anything other than a reference (including a const reference), the two can mean different things.

Edit: Sorry, I linked to the wrong post. Try this one. The problem arises from the fact that a T const & can bind to a temporary instead of the "real" object, so what happened with the code above was that it created a temporary, copied the object into it, bound the reference to it, destroyed the temporary, then returned the (now dangling) reference.

Upvotes: 2

zildjohn01
zildjohn01

Reputation: 11515

Why should it be const? If you're assigning to it, obviously it's modifiable. That would be artifically limiting.

As for use cases, why not:

T &local = t1 = t2 = t3;

In this example, local isn't const.

Upvotes: 2

Khaled Alshaya
Khaled Alshaya

Reputation: 96879

Most probably because this is how the native types of the language work. e.g.:

int x = 0, y = 1, z = 2;
(x = y) = z;

AFAIK, Dr. Stroustrup said that it is a good thing to have consistency in the language. i.e. user-defined types should behave just like native types.

Upvotes: 8

wendazhou
wendazhou

Reputation: 305

If we consider three auto_ptr a, b and c, the operator = has to return a non-const reference so that you can do multiple assigns since assigning the pointer to another modifies the first.

so if we have a = b = c, the following happens: c is assigned to b (c is modified to point to null), the operator returns a reference to b the reference returned by (b = c) is assigned to a, it is thus modified to point to null, which is only possible if the reference is non-const.

Upvotes: 0

outmind
outmind

Reputation: 829

I've spent some time and here is my example:

class A
{
public:
    const A& operator= (const A& a) {return *this;}
};

int main(int argc, char* argv[])
{
    A a1;
    A& a2 = a1;
    A& a3 = (a2 = a1);
}

and the compiler output: : error C2440: 'initializing' : cannot convert from 'const A' to 'A &'

I've checked it on MS VS 2010, but is it true on other platforms? And if this example is sufficient condition for = to be non const?

Upvotes: 2

CB Bailey
CB Bailey

Reputation: 791989

One good reason is that one of the requirements in the standard for a class X to be useable in the standard containers is that the expression a = b must have type X& (where a is an lvalue of type X and b is an rvalue of type X).

Upvotes: 11

Related Questions