Question

I have read a lot of articles about return value optimization. Yet I'm not sure to fully understand if this is what takes place in the following case (the addresses are actually always identical):

#include "stdafx.h"

class Type
{
public:
    Type(int a) { m_a = a; }
private:
    Type(const Type & other) {}
    int m_a;
};

class Base
{
public:
    Base() : instance(42) {}
    virtual Type & GetType()
    {
        printf("Base: Address of instance: %i\n", &instance);
        return instance;
    }

private:
    Type instance;
};

class Derived : public Base
{
public:
    virtual Type & GetType()
    {
        printf("Derived\n");
        return Base::GetType();
    }
};

int main()
{
    printf("Base class\n");
    Base b;
    printf("Main: Address of instance: %i\n", &(b.GetType()));

    printf("\nDerived class\n");
    Derived d;
    printf("Main: Address of instance: %i\n", &(d.GetType()));
}

Does returning by reference always ensure no copy constructor is called?
Or is RVO taking place here?

Was it helpful?

Solution 2

Does returning by reference always ensure no copy constructor is called?

Yes. When you pass or return by reference (as opposed to the passing/returning by value), no copy is being constructed.

is RVO taking place here?

Since you return by reference, RVO has nothing to do with it here. RVO is an optimization technique that consists in elimination of a redundant copy being created while returning by value.

RVO might take a place if you have function like this:

Type GetType()
{
    Type instance;
    //...
    return instance;
}
//...
Type t = GetType();

then with RVO the compiler would try to eliminate the redundant copy constructor and destructor calls which means that the local instance from the GetType function would be assigned into variable t without a copy being created.

OTHER TIPS

Does returning by reference always ensure no copy constructor is called?

RVO is an optimization technique. It is not guaranteed by the standard. Most compilers will apply RVO when you return by value.

virtual Type & GetType()
        ^^^^^^

You are returning by reference here, which means no copy needs to be created so there is no overhead of copy constructor call and hence no chance or scope of RVO.

the addresses are actually always identical

The addresses are actually always identical because they are addresses of the same class member.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top