一般,线程都是全局函数,那要想在线程中使用类成员函数怎么办呢?
解决途径是: 将类的指针作为参数 传递给线程函数。
SearchProcess()是CMainFrame类成员函数
SearchThread(LPVOID pParam) 线程函数
CMainFrame::Fun() -------- 当调用此函数时,执行线程
方法一: 全局函数
void CMainFrame::Fun()
{
AfxBeginThread(SearchThread,this);
}
//全局函数 不能访问类的私有变量
UINT SearchThread(LPVOID pParam) //全局函数
{
CMainFrame* pMainFrm = (CMainFrame*)pParam;
pMainFrm->SearchProcess();
return 1;
}
方法二: 静态成员函数
static UINT SearchThread(LPVOID pParam); //搜索线程
静态成员函数不可以调用类的非静态成员。因为静态成员函数不含this指针。
但此处,将对应指针传过来, 因此,可以通过指针调用其他成员
UINT CMainFrame::SearchThread(LPVOID pParam) //静态成员函数
{
CMainFrame* pMainFrm = (CMainFrame*)pParam;
pMainFrm->SearchProcess();
return 1;
}
void CMainFrame::Fun()
{
<strong>AfxBeginThread</strong>(SearchThread,this);
}
方法三: 友元函数
友元函数 可以访问类的私有数据等
friend UINT SearchThread(LPVOID pParam); //搜索线程
UINT SearchThread(LPVOID pParam) //友元函数 可以访问类的私有变量
{
CMainFrame* pMainFrm = (CMainFrame*)pParam;
pMainFrm->SearchProcess();
return 1;
}
void CMainFrame::Fun()
{
AfxBeginThread(SearchThread,this);
}
这三种方法 使用的函数类型不同, 但其中心思想都是一致的
其策略为: 将类对象的指针传递到线程中, 通过此指针 调用类成员函数
注意: 类成员函数SearchProcess() 不要出现求取其他视图中对象地址情况
而要将其,作为类变量,在初始化中赋值
比如, 此函数如果用到其他视图,则要在初始化中为其它视图指针赋值,而不要在此函数中赋值
错误方式:
void CMainFrame::SearchProcess()
{
CMyView * pMyView=(CMyView*)m_SplitterWnd.GetPane(0,1); //此处赋值是错误的 ,而应在OnInitialUpdate 中为类变量赋值
}
正确方式:
void CMainFrame::OnInitialUpdate(void)
{
pMyView=(CMyView*)m_SplitterWnd.GetPane(0,1);
}
四 传递多个参数
由于
AfxBeginThread(thread,pParm);
传递的参数只是一个指针,因此当传递多个参数时,可以设置一结构体保存各个参数
struct ThreadPram
{
CMainFrame* pFram;
CTreeCtrl * pCtrl;
HTREEITEM hItem;
}Param;
Param.pFram=this;
Param.pCtrl=pCtrl;
Param.hItem=hItem;
AfxBeginThread(PostThread,&Param);
//线程参数
struct ThreadPram
{
CMainFrame* pFram;
CTreeCtrl * pCtrl;
HTREEITEM hItem;
};
//线程函数
UINT PostThread(LPVOID parm)
{
ThreadPram *pThreadPram=(ThreadPram*)parm;
CMainFrame *pMainFrm=pThreadPram->pFram;
pMainFrm->TreeVisitPost (pThreadPram->pCtrl,pThreadPram->hItem);
return 1;
}
但是 ,在调试时发现,上述传参会有问题,原因是结构体变量是局部变量,退出此函数,进入线程函数执行时,结构体已经撤销,因此传递的值也就不正确了。
解决方法,将结构体声明为全局变量,也不传参了,直接用这个全局变量保存数据
//线程参数
struct ThreadPram
{
CMainFrame* pFram;
CTreeCtrl * pCtrl;
HTREEITEM hItem;
};
//全局结构体变量这样赋值时, 编译通过
struct ThreadPram m_Param={NULL,NULL,NULL};
//全局结构体变量 这样赋值时编译不通过 不知道为什么???
// struct ThreadPram m_Param;
// m_Param.pFram=NULL;
// m_Param.pCtrl=NULL;
// m_Param.hItem=NULL;
int m_threadStatus=1;
//线程函数
UINT PostThread(LPVOID parm)
{
// ThreadPram *pThreadPram=(ThreadPram*)parm;
CMainFrame *pMainFrm=m_Param.pFram;
pMainFrm->TreeVisitPost (m_Param.pCtrl,m_Param.hItem);
m_threadStatus=1;
return 1;
}
//开始启动线程 遍历文章 进行发布
void CMainFrame::beginVisit(CTreeCtrl* pCtrl,HTREEITEM hItem)
{
if(m_threadStatus)
m_threadStatus=0;
else
return;
m_Param.pFram=this;
m_Param.pCtrl=pCtrl;
m_Param.hItem=hItem;
AfxBeginThread(PostThread,NULL);
}