以下の例では、問題を最小限に抑えようとしましたが、A、B、C、D の 4 つのクラスがあります。、継承階層を形成します
プログラムが起動すると、クラスDのオブジェクト dが作成され、 Dクラスのテストメソッドが呼び出されます。このメソッドは、Cクラスの呼び出し元メソッドを呼び出します。このメソッドは、メンバ関数ポインタを使用して正しいfメソッドを呼び出そうとします。この場合、クラスDに関連付けられたfメソッドを呼び出す必要がありますが、クラスBに関連付けられたメソッドを呼び出します。
どうして ?
class A {
public:
virtual void f() = 0;
};
class B : public A{
public:
virtual void f() { cout << "IN B" << endl;}
};
class C : public B{
public:
virtual void f() { B::f(); cout << "IN C" << endl; }
virtual void caller(){
void (A::*cb)() = NULL;
cb = &A::f;
(this->*cb)();
}
};
class D : public C{
public:
virtual void f() { C::f(); cout << "IN D" << endl; }
void test(){
caller();
}
};
int main(){
D d;
d.test(); // Why does this prints only "IN B"
return 0;
}
更新:コードは実際に機能します。問題は提示されたコードに起因するものではなく、クラス A、B、C を提供するライブラリとクラス D を提供するライブラリとの間のバージョンの不一致に起因するようです。