2011-01-12 70 views
5

正如标题所示。 以下是我的代码框架。在C++中运行类成员函数的线程

class CLASS 
{ 
public: 
    void A(); 
private: 
    DWORD WINAPI B(LPVOID); 
}; 

void CLASS::A() 
{ 
    DWORD (WINAPI CLASS::*thread)(LPVOID) = &CLASS::B; 
    ... 
    CreateThread(NULL, 0, thread, &arg, 0, NULL); 
    ... 
} 

函数B需要CLASS的成员变量。
但我编译这个时有错误代码。
这是“无法将参数3从'DWORD(__stdcall CLASS :: *)(LPVOID)'转换为'LPTHREAD_START_ROUTINE'”或类似的东西。
我不知道它在英语环境中是否一样。

有人可以帮忙吗?

回答

3

你必须使该成员功能static

这里的问题是,每个非静态成员函数都有一个隐含的this参数,这实际上是编译器试图告诉你的 - 你的nin-static成员函数的签名与你期望的不同。

另请参阅this answer to a closely related question

+3

和运算开始前得到任何聪明的想法 - 非静态类成员函数指针是*怪异*。不仅调用约定与简单的`func(classname * this,...)`不同,_pointer representation_很奇怪 - 在某些情况下,类成员函数指针最终可能是普通函数指针的2倍,所以甚至不考虑迫使演员:) – bdonlan 2011-01-12 08:40:05

10

如果是成员函数,则必须将回调函数定义为static函数!


更好的设计:定义一个可重用的类!

从我previous answer:(带小的修改)

更妙的是定义与纯虚函数run()一个可重用的由衍生线程类实现。这是应该如何来设计:

//runnable is reusable class. All thread classes must derive from it! 
class runnable 
{ 
public: 
    virtual ~runnable() {} 
    static DWORD WINAPI run_thread(LPVOID args) 
    { 
     runnable *prunnable = static_cast<runnable*>(args); 
     return prunnable->run(); 
    } 
protected: 
    virtual DWORD run() = 0; //derived class must implement this! 
}; 

class Thread : public runnable //derived from runnable! 
{ 
public: 
    void newthread() 
    { 
     CreateThread(NULL, 0, &runnable::run_thread, this, 0, NULL); 
    } 
protected: 
    DWORD run() //implementing the virtual function! 
    { 
     /*.....your thread execution code.....*/ 
    } 
} 
+0

我会使用模板,而不是运行时继承。但总体思路是正确的。 – Puppy 2011-01-12 09:18:48

+0

@DeadMG:你的意思是CRTP? – Nawaz 2011-01-12 09:30:17

11

严重的是,使用std ::线程(或升压::线程,如果你的编译器不支持它尚未):

class CLASS 
{ 
public: 
    void A(); 
private: 
    void B(your args go here); 
}; 

void CLASS::A() 
{ 
    boost::thread(&CLASS::B, this, your args go here); 
}