I need to get a shared_ptr
from this
, which is easy for a parent class. But when you start deriving from this class - the issue is more difficult.
You get this error:
member 'shared_from_this' found in multiple base classes of different types
return this->shared_from_this(); ^
note: member found by ambiguous name lookup
How should I approach this?
#include <memory>
struct AAA : std::enable_shared_from_this<AAA>
{
auto getA() -> std::shared_ptr<AAA> { return this->shared_from_this(); }
};
struct BBB : AAA, std::enable_shared_from_this<BBB>
{
auto getB() -> std::shared_ptr<BBB> { return this->shared_from_this(); }
};
EDIT:
The reason for this convoluted code, is that I want my API to be designed in such way that you have setters - that return "self" and then you have chainability. Originally the setters would return a reference to self, but then code looks ugly (see the conversion from a pointer, to a reference):
// Before
auto a = std::make_shared<AAA>();
a->set_attrZ(1)
.set_attrK(2);
auto b = std::make_shared<BBB>();
b->set_attr1A(1)
.set_attrB(2)
.set_callback(()[]{ /* */ });
// After
auto a = std::make_shared<AAA>()
-> set_attrZ(1)
-> set_attrK(2);
auto b = std::make_shared<BBB>()
-> set_attrA(1)
-> set_attrB(2)
-> set_callback( ()[]{ /* */ });
// note that in some cases you might not need to maintain the reference - this may download a json from server and handle the data in the callback.
std::make_shared<BBB>()
-> set_attrA(1)
-> set_attrB(2)
-> set_callback( ()[]{ /* */ })
-> do_some_work();
I think you want:
struct BBB : AAA
{
auto getB() -> std::shared_ptr<BBB> {
auto spA = getA();
auto spB = std::static_pointer_cast<BBB>(spA);
return spB;
}
};
Or this:
struct BBB : AAA, std::enable_shared_from_this<BBB>
{
auto getB() -> std::shared_ptr<BBB> {
std::enable_shared_from_this<BBB>* sftB = this;
return sftB->shared_from_this();
}
};
I like the former better than the latter. The former doesn't create such a muddled inheritance tree.