Is there a way to create a derived instance from a base instance?

I want to add some basic information to a derived class on which it can be based. A derived class does not have to worry about initializing this information; it should only be there.

This in itself could easily be obtained through inheritance. But the problem is that the base class itself does not know the meaning. Instead, they should be passed as a parameter. However, since the derived class does not have to worry about this, tunneling parameters through the derived constructor, which calls the base constructor with it, is not an option.

The only solution I can think of is to make the information available statically so that the base class can get it without help. But I would like to avoid this.

Is there a way to first create and initialize a base class and then expand the instance to a derived type? If not, how can I achieve this order of creation and dependencies using the available C ++ features?

#include <string> #include <iostream> using namespace std; class Base { public: Base(string name, int age) : name(name), age(age) {} protected: const string name; int age = 0; }; class Derived : public Base { Derived() { // No parameters here, no call to base constructor cout << "My name is " << name << " and I'm " << age << "." << endl; } } Base base("Peter", 42); Derived derived(base); // "My name is Peter and I'm 42." 
+6
source share
3 answers

“Information should just“ sound ”to me as if it admits two possible interpretations:

  • Information is virtually globally constant and can be hardcoded:

     Derived() : Base("Peter", 42) {} 
  • What you really had in mind was that "the base should only be there":

     Derived(const Base & b) : Base(b) {} 
+6
source

Extending an already allocated type to a derived type is not possible for any reason: if the added fields are of a derived type, how would you determine the correct down payment size?

The only way possible is to use a constructor that accepts an instance of Base or perhaps operator= .

However, you might consider using composition over inheritance in this example. If Base serves only as a template for Derived , this is not a good example of an inheritance relationship.

+5
source

One option is to use composition, meaning Base will be an instance variable of Derived :

 #include <string> #include <iostream> using namespace std; class Base { public: Base(string name, int age) : name(name), age(age) {} const string name() { return name; } int age() { return age; } protected: const string name; int age = 0; }; class Derived { Derived(Base b): base(b) { // No parameters here cout << "My name is " << base.name() << " and I'm " << base.age() << "." << endl; } private: Base base; } Base base("Peter", 42); Derived derived(base); // "My name is Peter and I'm 42." 

Note that Derived no longer extends Base (perhaps names should be changed), and that every instance variable call in Base now a method call.

+3
source

Source: https://habr.com/ru/post/974717/


All Articles