Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there a mechanism in C++ to make a full copy of a derived class from a base class pointer without dynamic memory allocation?

Consider the following example, where object slicing occurs during dereference of a base pointer.

#include <stdio.h>

class Base {
  public:
    virtual void hello() {
        printf("hello world from base\n");
    }
};
class Derived : public Base{
  public:
    virtual void hello() {
        printf("hello world from derived\n");
    }
};

int main(){
    Base * ptrToDerived = new Derived;
    auto d = *ptrToDerived;
    d.hello();
}

I want the variable d to hold an object of type Derived instead of an object of type Base, without dynamic memory allocation, and without an explicit cast.

I have already looked at this question, but the solution proposed in the answer requires dynamic memory allocation, because it returns a pointer to the new object, instead of the value of the new object.

Is this possible in C++11?

like image 439
merlin2011 Avatar asked Jan 07 '23 01:01

merlin2011


2 Answers

No, it's not possible, because if d does not have dynamic storage duration, then it must have static, thread, or automatic storage duration, and in all of those cases, the type of the object is known at compile time. In your case, you want the type of the object to be determined at runtime, since ptrToDerived may point to a Base object or a Derived object or to an object of some other class derived from Base.

If your concern is about lifetime and memory leaks, just have clone return a std::unique_ptr<Base> instead of Base*.

like image 129
Brian Bi Avatar answered Jan 25 '23 20:01

Brian Bi


I guess you mean that you want auto to deduce to D.

However this is not possible: all types must be known at compile-time. Imagine if the code were:

Base *b = some_func();
auto d = *b;

There's no way the compiler can know the dynamic type of what b points to, because it might not be decided until runtime.

like image 34
M.M Avatar answered Jan 25 '23 20:01

M.M