Using shared_ptr with multiple inheritance classes

I have a class that inherits two interfaces:

class Multi : public IFoo, public IBar { public: virtual ~Multi(); // Foo part virtual void fooMethod(); // ... // Bar part virtual void barMethod(); // ... }; 

Unfortunately, this class cannot be decomposed into two separate classes for each interface. In fact, in the class implementation these objects (Foo and Bar) are closely related, but in the future they may become separate.

Another class wants to use the Multi-class, pointing to IFoo and IBar:

 class ClientClass { public: ClientClass(); // constructor // smth private: std::shared_ptr<IFoo> foo_; std::shared_ptr<IBar> bar_; }; 

In the constructor, I am doing something like:

 ClientClass::ClientClass(){ auto pMulti = new Multi; foo_ = std::shared_ptr<IFoo>(pMulti); bar_= std::shared_ptr<IBar>(pMulti); } 

But each of these common pointers has a separate reference counter, and this leads to the removal of the already deleted class destruction pointer, am I correct?

  • How do I treat him?
  • What is best suited for this?
+6
source share
2 answers
 ClientClass::ClientClass() { auto pMulti = std::make_shared<Multi>(); foo_ = pMulti; bar_ = pMulti; } 

will ensure that they have the same reference count. You can see it for yourself:

 #include <iostream> #include <memory> class Base1{}; class Base2{}; class Derived : public Base1, public Base2 {}; int main() { auto derived = std::make_shared<Derived>(); std::shared_ptr<Base1> base1 = derived; std::shared_ptr<Base2> base2 = derived; std::cout << "base1 usecount = " << base1.use_count() << '\n'; std::cout << "base2 usecount = " << base2.use_count() << '\n'; std::cout << "derived usecount = " << derived.use_count() << '\n'; return 0; } 

gives:

 base1 usecount = 3 base2 usecount = 3 derived usecount = 3 
+8
source

I don’t know exactly what you want to do with these pointers, but an alternative solution would be to save std::unique_ptr<multi> multi_; and the presence of several interface functions that static apply to simple pointers or links:

 IFoo& ClientClass::get_ifoo() { return *(static_cast<IFoo*>(multi_.get())); } IBar& ClientClass::get_ibar() { return *(static_cast<IBar*>(multi_.get())); } 

Until you exit the class and call delete[] on them, this should be completely safe.

0
source

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


All Articles