我有一个奇怪的问题,使用多态性。 我有一个实现静态方法的基类。由于各种原因,此方法必须是静态的。基类还有一个纯虚方法run()
,它由所有扩展类实现。我需要能够从静态类调用run()
。C++中的多态性静态方法
问题当然是静态类没有这个指针。该方法可以通过void *参数传递。我一直试图想出一个聪明的方法来将run方法传递给它,但迄今为止没有任何工作。也尝试将其传递给它。这个问题是,我将不得不实例化它,这需要扩展类的知识。这打破了多态性的全部目的。
关于如何去做这件事的任何想法?
我有一个奇怪的问题,使用多态性。 我有一个实现静态方法的基类。由于各种原因,此方法必须是静态的。基类还有一个纯虚方法run()
,它由所有扩展类实现。我需要能够从静态类调用run()
。C++中的多态性静态方法
问题当然是静态类没有这个指针。该方法可以通过void *参数传递。我一直试图想出一个聪明的方法来将run方法传递给它,但迄今为止没有任何工作。也尝试将其传递给它。这个问题是,我将不得不实例化它,这需要扩展类的知识。这打破了多态性的全部目的。
关于如何去做这件事的任何想法?
不要把它作为一个void *指针,它传递的指针(或引用)的基类:
class BaseClass
{
public:
static void something(BaseClass* self) { self->foo(); }
virtual void foo() = 0;
};
为什么不传递对象的引用而不是方法,例如
static void func(BaseObject& o)
{
o.run();
}
IMO,最好的办法是摆脱静态方法。找到一个方法,你是金。
这通常发生在你必须通过C API松鼠C++对象时。一个典型的例子是一个线程类。
这里是这样做的标准成语:
/** calls thread_func in a new thread passing it user_data as argument */
thrd_hdl_t c_api_thread_start(int (*thread_func)(void*), void* user_data);
/** abstract thread base class
* override my_thread::run to do work in another thread
*/
class my_thread {
public:
my_thread() hdl_(c_api_thread_start(my_thread::thread_runner,this)) {}
// ...
private:
virtual int run() = 0; // we don't want this to be called from others
thrd_hdl_t hdl_; // whatever the C threading API uses as a thread handle
static int thread_runner(void* user_data)
{
my_thread* that = static_cast<my_thread*>(user_data);
try {
return that->run();
} catch(...) {
return oh_my_an_unknown_error;
}
}
};
但愿帮助吗?
不错的代码片段,但使用'static_cast'从'void *'强制转换为另一个指针会更好吗? – 2011-03-29 07:09:06
@Eli:哎呀。你能做到吗?我不知道。如果你确定,我一定会改变它。 (随意自己改变。) – sbi 2011-03-29 09:25:11
你当然*可以*做到这一点(因为'void *'是静态转换 - 可以指向任何指针)。但是,你是否真的想成为一个良好的做法。见http://stackoverflow.com/questions/310451/should-i-use-static-cast-or-reinterpret-cast-when-casting-a-void-to-whatever因为这是你的答案,我会让你决定:) – 2011-03-29 13:42:12
我想你的意思是“静态方法”在第一段最后? – unwind 2009-10-09 14:44:54
Ori,你反对将'this'传递给静态方法,因为“然后我必须实例化它”,但是你想调用虚拟的'run'方法。你不能在没有实例的情况下调用一个虚拟方法,所以你将不得不实例化这个类。静态方法不需要知道*哪个*类被实例化;正如克里斯的回答所证明的,它只是接收一个基类指针。 – 2009-10-09 15:13:11