Can an abstract class be a member of another concrete class as a composition relation? C ++

P is an abstract class, I want to make it a member of class A, which is an ordinary concrete class. Is it possible, yes, how. Communication - composition Thank you for your help

+4
source share
5 answers

Since P is abstract, you can never create an object of this type. However, you can save a pointer to P as a member of class A ; this pointer element can then point to an instance of a (specific) subclass of P

+5
source

Not. Composition ratio implies that the Client class actually contains a member variable of type AbstractClass.

I assume that your definition of "abstract class" is common to a class with at least one pure virtual function. This means that it cannot be a member of a particular class, because this class cannot be created.

You can have a link or a pointer to an abstract class, including one where life management is very similar to the composition relation for you, for example:

  class Client { public: Client(AbstractClass* adopted) : ownedAbstract(adopted) {} ... std::shared_ptr<AbstractClass> ownedAbstract; }; class AbstractClass{ public: virtual ~AbstractClass()=0; // virtual dtor needed so can delete AbstractClass* }; class AbstractSubclass : public AbstractClass{ public: virtual ~AbstractSubclass(); }; Client fred(new AbstractSubclass); 
+3
source

You cannot create objects of an abstract class. therefore you cannot do this. However, you can have a class member that is a pointer to an abstract class.

Here is an example code to prove this:

 class abstract { virtual void somethiing() = 0; }; class concrete { abstract obj; }; int main() { return 0; } 

Compilation:

prog.cpp: 8: error: cannot declare the "concrete :: abstract type" object field abstract | prog.cpp: 2: note: because the following virtual functions are pure in abstract:
prog.cpp: 3: note: virtual void abstract :: somethiing ()

Compiled sample:

 class abstract { virtual void somethiing() = 0; }; class concrete { abstract *ptr; }; int main() { return 0; } 
+2
source

You cannot create an abstract class explicitly in another class. But you can give pure virtual functions to an abstract base class a definition that, in turn, can be called in a derived class in a way that is very similar to composition.

Effective C ++ programming (second edition) suggests that the reason pure virtual functions in abstract classes can have a body (definition) is because the inheriting class can provide an implementation of a function that calls the pure virtual version in its body.

If you have access to the book, see paragraph 36.

Here is an example that I put together. It demonstrates how to achieve the composition of an object by inheriting an interface from an abstract class and using its implementation to compose an implementation of a function definition in a derived class.

 #include <iostream> class P { public: virtual void say_hello() = 0; }; void P::say_hello() { std::cout << "Hello world!" << std::endl; } class A :public P { public: void say_hello() { P::say_hello(); } }; int main() { A x; x.say_hello(); return 0; } 

The result will be that class A 'say_hello' will call P a purely virtual version of the function with the same name. Therefore, the call to say_hello () will end with the print of Hello world.

Public and protected element data in an abstract class are also available for the derived class.

 #include <iostream> #include <string> using namespace std; class P { public: P() { audience = "world"; } virtual void say_hello() = 0; protected: string audience; }; void P::say_hello() { cout << "Hello " << audience << "!" << endl; } class A :public P { public: void say_hello() { P::say_hello(); } void say_goodbye() { cout << "Goodbye " << audience << "." << endl; } }; int main() { A x; x.say_hello(); x.say_goodbye(); return 0; } 
0
source

I understand that this sounds asymmetrical, but the answer is no. An abstract class cannot be created and therefore cannot be used as a member of another class.

Asymmetry is obvious because you can use an abstract class as a base, and even a basic subobject of an object must be created; but in this case the operation is allowed, and just the resulting class automatically becomes abstract.

However, the logical reason is that in this last case, you can extract a specific class from this new abstract class, while in the first case, the C ++ language syntax will have nothing to do with replacing the included object type with the class object obtained from this type.

In a sense, the subobject type of the database / a class can subsequently be changed in the inheritance hierarchy, while the subobject type of the regular element is fixed.

Of course, you can use a pointer or a link to an abstract class in the object, because in this case the real type of the object will be concrete and will be known only at runtime.

0
source

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


All Articles