First if all, of the polymorphism answers I find, it's always like "if the base function is not virtual and the derived object is stored in a pointer of type base, then you cannot call the derived function". But they never tell you what to do when you want to do exactly that. And that's what I need to do.
I have a base class B
that I have no control over. It's open source (TwoWire
from Arduino library) and it will not work for others if I make local modifications.
I have a derived class D
and a user class U
that I both have control over.
In effect, I want the user to use my class U
transparently with either a B
or a D
as parameter, store it in a member, and use it in member functions.
My futile attempt before learning virtual
is required on the base class:
#include <iostream>
using namespace std;
class B {
public:
void foo() { cout << "base foo\n"; };
};
class D : public B {
public:
void foo() { cout << "derived foo\n"; };
};
class U {
public:
U(B *b) : b(b) { }
void work() { b->foo(); }
private:
B *b;
};
int main() {
B b; U u1{&b}; u1.work(); // "base foo"
D d; U u2{&d}; u2.work(); // I need this to somehow print "derived foo"
return 0;
}
I could solve this by making an abstract wrapper class and two sub-classes that wrap either B
or D
, but that would bring the total number of custom classes to 5. I'm hoping for a solution of just 2 custom classes (or at most 3).
N.B. I'm just starting to learn C++, coming from Java
Since making the member function virtual
is not a possibility, you have to simulate dynamic dispatch with type erasure:
#include <functional>
class U {
public:
template <class C>
U(C* p)
: f{[p]{ p->foo(); }}
{
}
void work()
{
f();
}
private:
std::function<void()> f;
};
(live demo)
Note that functions in Java are virtual by default. Not in C++.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With