我有两个类Base
和Derived
相互继承。在Base
中我想创建一个执行类的成员函数Handle
的线程(TThread
是ROOT的MT库)。我想在Derived
中覆盖这个句柄函数,但是我的程序总是从基类而不是从派生类中执行函数。如何更改它以便执行被覆盖的句柄?
以下是代码:
#include "TThread.h"
#include <iostream>
using namespace std;
class Base
{
public:
Base()
{
thread = new TThread("BaseClass", (void(*)(void*))&Handle,(void*)this);
thread->Run();
}
private:
TThread *thread;
static void* Handle(void *arg)
{
cout<<"AAAA"<<endl;
}
};
class Derived : public Base
{
public:
Derived() : Base(){}
private:
static void* Handle(void *arg)
{
cout<<"BBBB"<<endl;
}
};
int main()
{
Derived *b = new Derived();
return 0;
}
答案 0 :(得分:2)
您正在尝试使用非virtual
函数实现多态性。
在基类构造函数中对Handle
的引用在编译时得到解析,始终指向Base::Handle
,无论运行时对象的具体类型是什么。这可以通过将Handle
从static
更改为virtual
功能来解决。
另一个问题是您正在尝试从基类构造函数创建线程。此时尚未完全构造派生对象,因此即使将其更改为Derived::Handle
函数,也无法以多态方式分派到virtual
。对此的快速解决方案是将线程构造移动到Base::startThread()
方法,并在构造函数返回后调用它。
答案 1 :(得分:1)
将Handle
虚拟为@ComicSansMS says,并引入静态成员函数来正确处理虚拟调度:
#include "TThread.h"
#include <iostream>
using namespace std;
class Base
{
public:
Base() : thread() {}
~Base() { wait(); }
void wait() {
if (thread)
{
thread->Join();
delete thread;
thread = NULL;
}
}
void start()
{
thread = new TThread("BaseClass", &Dispatch, this);
thread->Run();
}
private:
TThread *thread;
virtual void Handle()
{
cout<<"AAAA"<<endl;
}
static void* Dispatch(void *arg)
{
static_cast<Base*>(arg)->Handle();
return NULL;
}
};
class Derived : public Base
{
public:
Derived() { start(); }
~Derived() { wait(); }
private:
virtual void Handle()
{
cout<<"BBBB"<<endl;
}
};
int main()
{
Derived b;
}