简体   繁体   English

C ++ —为什么operator =返回对* this的引用而不是对* this的对象?

[英]C++ — why the operator= return a reference to *this rather than an object to *this?

class MyClass {
  public:
    ...
    MyClass & operator=(const MyClass &rhs); // return MyClass&
    ...
  }

why not 为什么不

class MyClass {
  public:
    ...
    MyClass  operator=(const MyClass &rhs); // return MyClass
    ...
  }

Is it the reason that it is more efficient to return by reference in this case? 是在这种情况下通过引用返回更有效的原因吗?

Thank you 谢谢

// * updated * // *更新*

I think I found the key reason as follows: 我认为我发现了以下关键原因:

int i1, it2, i3;
(i1 = i2) = i3; // i3 will be assigned to i1

If the return type of operator= is MyClass rather than MyClass&, then the following statement doesn't perform the same as the internal data type. 如果operator =的返回类型是MyClass而不是MyClass&,则以下语句与内部数据类型的执行不同。

MyClass mc1, mc2, mc3;

(mc1 = mc2) = mc3;

It is considered as a good practice by following the rules used by the built-in types. 通过遵循内置类型使用的规则,这被认为是一种好的做法。

// *** update ***

#include "stdafx.h"
#include <iostream>

using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{
    int i1, i2, i3;

    i1 = 0;
    i2 = 2;
    i3 = 3;

    (i1 = i2) = i3;

    cout << "i1: " << i1 << endl;
    cout << "i2: " << i2 << endl;
    cout << "i3: " << i3 << endl;

    return 0;
}

// output from VS2010
/*
i1: 3
i2: 2
i3: 3
*/

What do you mean by your "why not"? 您的“为什么不”是什么意思? It is really up to you. 真的取决于您。 If you want, you can return the copy of the object instead of the reference. 如果需要,可以返回对象的副本而不是引用。 There's nothing wrong with that, except that it might indeed prove to be less efficient. 这没什么不对的,除了它确实确实效率较低。

In many cases people prefer to return the reference because it is closer to the semantics of the built-in assignment operator. 在许多情况下,人们更喜欢返回引用,因为它更接近内置赋值运算符的语义。 The built-in operator returns an lvalue, which means that you can write code like 内置运算符返回一个左值,这意味着您可以编写如下代码

int a, b = 0;
int *p = &(a = b);
// `p` now points to `a`

Admittedly it is not very useful, but still if you want to preserve that lvalue semantics, you need to return a reference from your assignment operator. 诚然,它不是很有用,但是仍然要保留左值语义,就需要从赋值运算符返回引用。

Update 更新资料

Your updated example is incorrect. 您更新的示例不正确。 The (i1 = i2) = i3 expression leads to undefined behavior, not to "i3 will be assigned to i1" as you seem to believe. (i1 = i2) = i3表达式会导致未定义的行为,而不是您似乎相信的那样不会导致“将i3分配给i1”。 It is true that the fact that assignment operator returns an lvalue is what allows you to compile expressions like (i1 = i2) = i3 . 的确,赋值运算符返回一个左值这一事实使您可以编译(i1 = i2) = i3类的表达式。 However, this specific expression is useless since the behavior is undefined. 但是,由于行为未定义,因此该特定表达式毫无用处。

In case of user-defined assignment, as in your (mc1 = mc2) = mc3 example, the behavior is defined but it is still far from being useful. 在用户定义的分配的情况下,如您的(mc1 = mc2) = mc3示例,行为已定义,但仍远没有用处。 Why would you want to do something like that? 你为什么要做这样的事情?

As long as, operator = receives argument as (const T&) , it's a valid operator overloading. 只要operator =接收作为(const T&) ,这就是有效的运算符重载。 You can return whatever value you want. 可以返回所需的任何值 For example, if I want to avoid consecutive object copying, I declare operator as, 例如,如果要避免连续复制对象,可以将operator声明为,

void operator = (const T& copy) { }

As soon as you attempt x = y = z; 只要您尝试x = y = z; compiler will throw error, but x = y; 编译器将抛出错误,但是x = y; is still valid! 仍然有效! Return value is based on your requirement; 返回值取决于您的要求; if you want you can return the same object or int or char* , it's up to you. 如果您想返回相同的对象或intchar* ,则取决于您。 Returning non const reference to *this is a popular convention. 返回非const引用*this是一种流行的约定。

My C++ days are long gone, but wouldn't you r syntax create a temporary copy of the class? 我的C ++时代早已过去,但是您不会使用语法创建类的临时副本吗?

hth hth

Mario 马里奥

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM