VC中CWinThread類和和createthread API的差別剖析。本站提示廣大學習愛好者:(VC中CWinThread類和和createthread API的差別剖析)文章只能為提供參考,不一定能成為您想要的結果。以下是VC中CWinThread類和和createthread API的差別剖析正文
本文實例講述了VC中CWinThread類和和createthread API的差別剖析,分享給年夜家供年夜家參考。詳細剖析以下:
CWinThread
CObject
└CCmdTarget
└CWinThread
CWinThread對象代表在一個運用法式內運轉的線程。運轉的主線程平日由CWinApp的派生類供給;CWinApp由CWinThread派生。別的,CWinThread對象許可一給定的運用法式具有多個線程。
CWinThread支撐兩種線程類型:任務者線程(Worker Thread)和用戶界面線程(UI thread)。任務者線程沒有收發新聞的功效(沒有新聞隊列):例如,在電子表格運用法式中停止後台盤算的線程。
用戶界面線程具有收發新聞的功效,並處置從體系收到的新聞。CWinApp及其派生類是用戶界面線程的例子。其它用戶界面線程也可由CWinThread直接派生。
CWinThread類的對象存在於線程的生計期。假如你願望轉變這個特征,將m_bAutoDelete設為FALSE。
要使你的代碼和MFC是完整線程平安的,CWinThread類是完整需要的。框架應用的用來保護與線程相干的信息的線程部分數據由CWinThread對象治理。因為依附CWinThread來處置線程部分數據(Thread Local Storage),任何應用MFC的線程必需由MFC創立。例如,由運轉時函數_beginthreadex創立的線程不克不及應用任何MFC API。
為了創立一個線程,挪用AfxBeginThread函數。依據你須要任務者線程照樣用戶界面線程,有兩種挪用AfxBeginThread的格局。假如你須要用戶界面線程,則將指向你的CWinThread派生類的CRuntimeClass的指針傳遞給AfxBeginThread。假如你須要創立任務者線程,則將指向掌握函數的指針和掌握函數的參數傳遞給AfxBeginThread。關於任務者線程和用戶界面線程,你可以指定可選的參數來修正優先級,客棧年夜小,創立標記和平安屬性。
AfxBeginThread線程將前往指向新的CWinThread對象的指針。
與挪用AfxBeginThread相反,你可以結構一個CWinThread派生類的對象,然後挪用CreateThread。假如你須要在持續創立和終止線程的履行之間反復應用CWinThread對象,這類兩步結構辦法異常有效。
CWinThread類成員
數據成員
m_bAutoDelete 指定線程停止時能否要燒毀對象
m_hThread 以後線程的句柄
m_nThreadID 以後線程的ID
m_pMainWnd 保留指向運用法式的主窗口的指針
m_pActiveWnd 指向容器運用法式的主窗口,當一個OLE辦事器被現場激活時
結構函數
CWinThread 結構一個CWinThread對象
CreateThread 開端一個CWinThread對象的履行
操作
GetMainWnd 查詢指向線程主窗口的指針
GetThreadPriority 獲得以後線程的優先級
PostThreadMessage 向別的的CWinThread對象傳遞一條新聞
ResumeThread 削減一個線程的掛起計數
SetThreadPriority 設置以後線程的優先級
SuspendThread 增長一個線程的掛起計數
可重載函數
ExitInstance 重載以停止線程終止時的清算任務
InitInstance 重載以完成線程實例的初始化
OnIdle 重載以停止線程特定的余暇操作
PreTranslateMessage 在新聞被發送到Windows函數TranslateMessage和DispatchMessage之前過濾新聞
IsIdleMessage 檢測特定的新聞
ProcessWndProcException 截獲線程新聞和敕令處置函數湧現的一切未處置的異常
ProcessMessageFilter 在特定的新聞達到運用法式之前截獲新聞
Run 線程的具有新聞收發功效的掌握函數,可重載以定制缺省的新聞輪回
AfxBeginThread和CreateThread詳細差別
詳細說來,CreateThread這個 函數是windows供給給用戶的 API函數,是SDK的尺度情勢.
AfxBeginThread,是編譯器對本來的CreateThread函數的封裝,用與MFC.
而_beginthread是C的運轉庫函數。
在應用AfxBeginThread時,線程函數的界說為:UINT _yourThreadFun(LPVOID pParam)
在應用CreateThread時,線程的函數界說為: DWORD WINAPI _yourThreadFun(LPVOID pParameter)。
兩個的本質都是一樣的,不外AfxBeginThread前往一個CWinThread的指針,就是說他會new一個CWinThread對象,並且這個對象是主動刪除的(在線程運轉停止時),給我們帶來的未便就是沒法取得它的狀況,由於隨時都有能夠這個指針指向的是一個曾經有效的內存區域,所以應用時(假如須要懂得它的運轉狀態的話)起首CREATE_SUSPENDED讓他掛起,然後m_bAutoDelete=FALSE,接著才ResumeThread,最初不要了delete誰人指針。
CreatThread就便利多了,它前往的是一個句柄,假如你不應用CloseHandle的話便可以經由過程他平安的懂得線程狀況,最初不要的時刻CloseHandle,Windows才會釋放資本(線程內查對象).
上面我們就來看一下AfxBeginThread函數的外部完成:
//啟動worker線程
CWinThread* AFXAPI AfxBeginThread(AFX_THREADPROC pfnThreadProc, LPVOID pParam,
int nPriority, UINT nStackSize, DWORD dwCreateFlags,
LPSECURITY_ATTRIBUTES lpSecurityAttrs)
{
ASSERT(pfnThreadProc != NULL);
CWinThread* pThread = DEBUG_NEW CWinThread(pfnThreadProc, pParam);
ASSERT_VALID(pThread);
if (!pThread->CreateThread(dwCreateFlags|CREATE_SUSPENDED, nStackSize,
lpSecurityAttrs))
{
pThread->Delete();
return NULL;
}
VERIFY(pThread->SetThreadPriority(nPriority));
if (!(dwCreateFlags & CREATE_SUSPENDED))
VERIFY(pThread->ResumeThread() != (DWORD)-1);
return pThread;
}
//啟動UI線程
CWinThread* AFXAPI AfxBeginThread(CRuntimeClass* pThreadClass,int nPriority, UINT nStackSize, DWORD dwCreateFlags, LPSECURITY_ATTRIBUTES lpSecurityAttrs)
{
ASSERT(pThreadClass != NULL);
ASSERT(pThreadClass->IsDerivedFrom(RUNTIME_CLASS(CWinThread)));
CWinThread* pThread = (CWinThread*)pThreadClass->CreateObject();
if (pThread == NULL)
AfxThrowMemoryException();
ASSERT_VALID(pThread);
pThread->m_pThreadParams = NULL;
if (!pThread->CreateThread(dwCreateFlags|CREATE_SUSPENDED, nStackSize,
lpSecurityAttrs))
{
pThread->Delete();
return NULL;
}
VERIFY(pThread->SetThreadPriority(nPriority));
if (!(dwCreateFlags & CREATE_SUSPENDED))
VERIFY(pThread->ResumeThread() != (DWORD)-1);
return pThread;
}
重要創立函數是 pThread->CreateThread(dwCreateFlags|CREATE_SUSPENDED, nStackSize,lpSecurityAttrs))
也就是 CWinThread::CreateThread。
願望本文所述對年夜家的VC法式設計有所贊助。