Edward Hu
Edward Hu

Reputation: 57

C++ return by reference stack allocation details

can someone walk through exactly what happens with the memory in this operator overload function? I am confused on how exactly the object created inside the operator function gets deallocated in the main.

Object& operator+(const Object& other) {
  Object o(*this); //create instance of o that deep copies first argument
  ...
  //copy contents of other and add onto o
  return o;
}
int main() {
  Object b;
  Object c;
  Object a = b + c;
}

Edit: to be more specific, isn't it bad practice to create a local object in a function and then return it by reference? Wouldn't that cause a memory leak?

Edit 2: I am referencing my textbook Data abstraction & problem solving with c++ carrano which suggests an operator + overload for LinkedLists in this format: LinkedList<ItemType>& operator+(const LinkedList<ItemType>& rightHandSide) const;. They implemented the method in the way I described.

Edit 2.5: the full method pseudocode given by the book:

LinkedList<ItemType>& operator+(const LinkedList<ItemType>& rightHandSide) const {
  concatList = a new, empty instance of LinkedList
  concatList.itemCount = itemCount + rightHandSide.itemCount
  leftChain = a copy of the chain of nodes in this list
  rightChain = a copy of the chain of nodes in the list rightHandSide
  concatList.headPtr = leftChain.headPtr
  return concatList
}

Edit 3: Asked my professor about this. Will get to the bottom of this by tomorrow.

Edit 4: The book is wrong.

Upvotes: 3

Views: 151

Answers (3)

Patrik H
Patrik H

Reputation: 459

Returning a reference to a local object

As everyone else correctly states, returning a reference to a local object results in undefined behaviour. You will end up with a handle to a destroyed function-scope object.

Returning references in arithmetic operators

If you think about it, a+b should give you a result, but it shouldn't change a nor b. C++ however leaves it up to you to define how operators work on your own types so it's possible to implement the behaviour you need. This is why the operator+ usually has to create a new object and can't return a reference.

Compound assignments (+=, -=, etc) on the other hand do change the object itself so a += b is changing a. This is why it's usually being implemented by returning a reference (not to a local object, but to the instance itself):

Object& Object::operator+=(const Object& rhs)
{
    // do internal arithmetics to add 'rhs' to this instance
    return *this; // here we return the reference, but this isn't a local object!
}

Upvotes: 3

Kariem
Kariem

Reputation: 780

It is simply undefined behavior.

In terms of what happens to memory, the memory will not be reserved to the object after the function returns (because the object is now out of scope).

So it can contain ANYTHING, including the same object by way of coincidence.

Upvotes: 2

Peter Stock
Peter Stock

Reputation: 450

It wouldn't cause a memory leak, but o gets destroyed when it goes out of scope, when the function returns. So the reference the caller has is junk. It might appear to work fine for a short time until the memory is overwritten later.

Upvotes: 2

Related Questions