Home > OS >  Should you overload the "=" operator by reference or with a temporary variable?
Should you overload the "=" operator by reference or with a temporary variable?

Time:08-26

Consider a class with just a single member for this example.

class tester
{
public:
    int tester_value;

    tester(){}

    tester(int test_val)
    {
      tester_value = test_val;
    } 
    

    tester(const tester & data) : tester_value(data.tester_value)
    {
      std::cout << "Copied!" << std::endl;
    }
};

I was curious as to the proper way to overload the = operator and why one way works and another does not.

For example, this operator overload does not seem to properly copy the data from one object to another.

Example 1:

tester operator=(const tester & data) const
{
  tester temp;    
  std::memcpy(&temp, &data, sizeof(tester));
  return temp;
}

However, this example works just fine.

Example 2:

tester& operator=(const tester & data)
{        
  tester_value = data.tester_value;

  return *this;
}

When using the following code to test each example...

  tester my_test = tester(15);
  
  tester my_second_test = tester(20);    
  
  my_test = my_second_test;
  
  std::cout << "my_test.tester_value:" << my_test.tester_value << std::endl;
  
  std::cout << "my_second_test.tester_value:" << my_second_test.tester_value << std::endl;

The result for example 1 will be:

15
20

While the result for example 2 will be:

20
20

So,

Question 1: Why is it that using a temporary variable and memcpy() does not work properly to copy the data from one object to another when overloading the = operator?

Question 2: What is the proper and most efficient way to do overload this operator?

I appreciate any explanation, I am still getting used to the C language.

Thanks in advance!

CodePudding user response:

Question 1: Why is it that using a temporary variable and memcpy() does not work properly to copy the data from one object to another?

This is because of the Golden Rule Of Computer Programming: "Your computer always does exactly what you tell it to do, instead of what you want it to do".

Tester A, B;

// ... at some point later.

A=B;

The instruction A=B instructs your computer to invoke A's operator= overload. In the overload, *this becomes A.

tester operator=(const tester & data) const
{
  tester temp;    
  std::memcpy(&temp, &data, sizeof(tester));
  return temp;
}

Nothing here tells your computer that anything in *this gets modified. Since you did not tell your computer to modify this->tester_value it does not get modified.

Nothing here effectively sets A.tester_value. Instead, some new object gets created and returned. That's what you told your computer to do, so that's what it does, no more no less. But the return value is not used for anything. The return value here is the value for the entire A=B; statement itself, which is not used for anything. It is the operator= itself that's responsible for assigning the new value of this object. It is not the return value from the operator= method that sets the new value of the object, it's the operator itself. In the operator= overload, what's on the right side of the = in the expression gets passed to operator= as a parameter, and what's on the left side of the = in the expression is *this.

Question 2: What is the proper and most efficient way to do overload this operator?

That's already answered by Stackoverflow's canonical on operating overloading. TLDR: it's "Example 2".

  • Related