I was doing some fun stuff with googlemock and decided to split my classes into pure virtual classes and concrete implementations to avoid needing to special casing for my mocks. However, the compiler started complaining that:
error: undefined reference to 'vtable for <ConcreteClass>'
I managed to reproduce the issue with the following:
simple.h:
namespace simple {
class InterfaceA {
public:
virtual ~InterfaceA() {}
virtual int MethodOne() const = 0;
};
class InterfaceB : public InterfaceA {
public:
~InterfaceB() override {}
virtual int MethodTwo() const = 0;
};
class ImplA : public InterfaceA {
public:
ImplA(int to_return);
~ImplA() override {}
int MethodOne() const override;
private:
int to_return_;
};
class ImplB : public InterfaceB, public ImplA {
public:
ImplB();
~ImplB() override {}
// int MethodOne() const override;
int MethodTwo() const override;
};
} // namespace simple
simple.cc
#include "simple.h"
namespace simple {
ImplA::ImplA(int to_return) : to_return_(to_return) {}
int ImplA::MethodOne() const { return to_return_; }
ImplB::ImplB() : ImplA(5) {}
// int ImplB::MethodOne() const { return ImplA::MethodOne(); }
int ImplB::MethodTwo() const { return 2; }
} // namespace simple
The issue was the bits I have commented out; once I added those things into the files, the compiler and my tests were happy. So intuitively this makes sense, as now there are concrete methods defined for the virtual ones, and the compiler previously doesn't/can't guess which super class methods I wanted.
My question is twofold:
- How does the specification of
ImplA::MethodOne()
allow it to be called as it isn't a static variable? - Is there an implicit
ImplA
pointer somewhere in theImplB
object at creation time that allows it to call a method onImplA
despite not being a static method?
Aucun commentaire:
Enregistrer un commentaire