国产一级a片免费看高清,亚洲熟女中文字幕在线视频,黄三级高清在线播放,免费黄色视频在线看

打開(kāi)APP
userphoto
未登錄

開(kāi)通VIP,暢享免費(fèi)電子書(shū)等14項(xiàng)超值服

開(kāi)通VIP
線(xiàn)程中CreateEvent和SetEvent及WaitForSingleObject的用...
線(xiàn)程中CreateEvent和SetEvent及WaitForSingleObject的用法 2008-08-11 10:56
分類(lèi):C++ 內(nèi)存 線(xiàn)程 指針 DLL
字號(hào):大 中  小
首先介紹CreateEvent是創(chuàng)建windows事件的意思,作用主要用在判斷線(xiàn)程退出,程鎖定方面.
CreateEvent
函功能描述:創(chuàng)建或打開(kāi)一個(gè)命名的或無(wú)名的事件對(duì)象.
EVENT有兩種狀態(tài):發(fā)信號(hào),不發(fā)信號(hào)。
SetEvent/ResetEvent分別將EVENT置為這兩種狀態(tài)分別是發(fā)信號(hào)與不發(fā)信號(hào)。
WaitForSingleObject()等待,直到參數(shù)所指定的OBJECT成為發(fā)信號(hào)狀態(tài)時(shí)才返回,OBJECT可以是EVENT,也可以是其它內(nèi)核對(duì)象。
當(dāng)你創(chuàng)建一個(gè)線(xiàn)程時(shí),其實(shí)那個(gè)線(xiàn)程是一個(gè)循環(huán),不像上面那樣只運(yùn)行一次的。這樣就帶來(lái)了一個(gè)問(wèn)題,在那個(gè)死循環(huán)里要找到合適的條件退出那個(gè)死循環(huán),那么是怎么樣實(shí)現(xiàn)它的呢?在Windows里往往是采用事件的方式,當(dāng)然還可以采用其它的方式。在這里先介紹采用事件的方式來(lái)通知從線(xiàn)程運(yùn)行函數(shù)退出來(lái),它的實(shí)現(xiàn)原理是這樣,在那個(gè)死循環(huán)里不斷地使用WaitForSingleObject函數(shù)來(lái)檢查事件是否滿(mǎn)足,如果滿(mǎn)足就退出線(xiàn)程,不滿(mǎn)足就繼續(xù)運(yùn)行。當(dāng)在線(xiàn)程里運(yùn)行阻塞的函數(shù)時(shí),就需要在退出線(xiàn)程時(shí),先要把阻塞狀態(tài)變成非阻塞狀態(tài),比如使用一個(gè)線(xiàn)程去接收網(wǎng)絡(luò)數(shù)據(jù),同時(shí)使用阻塞的SOCKET時(shí),那么要先關(guān)閉SOCKET,再發(fā)送事件信號(hào),才可以退出線(xiàn)程的。
當(dāng)然我感覺(jué)重要應(yīng)用方面還是用來(lái)鎖定,實(shí)現(xiàn)所謂的pv功能。
下面介紹函數(shù)功能,參數(shù)等
1.CreateEvent
函數(shù)功能描述:創(chuàng)建或打開(kāi)一個(gè)命名的或無(wú)名的事件對(duì)象
函數(shù)原型:
HANDLE CreateEvent(
LPSECURITY_ATTRIBUTES lpEventAttributes,   // 安全屬性
BOOL bManualReset,   // 復(fù)位方式
BOOL bInitialState,   // 初始狀態(tài)
LPCTSTR lpName   // 對(duì)象名稱(chēng)
);
參數(shù):
lpEventAttributes:
[輸入]一個(gè)指向SECURITY_ATTRIBUTES結(jié)構(gòu)的指針,確定返回的句柄是否可被子進(jìn)程繼承。如果lpEventAttributes是NULL,此句柄不能被繼承。
Windows NT/2000:lpEventAttributes的結(jié)構(gòu)中的成員為新的事件指定了一個(gè)安全符。如果lpEventAttributes是NULL,事件將獲得一個(gè)默認(rèn)的安全符。
bManualReset:
[輸入]指定將事件對(duì)象創(chuàng)建成手動(dòng)復(fù)原還是自動(dòng)復(fù)原。如果是TRUE,那么必須用ResetEvent函數(shù)來(lái)手工將事件的狀態(tài)復(fù)原到無(wú)信號(hào)狀態(tài)。如果設(shè)置為FALSE,當(dāng)事件被一個(gè)等待線(xiàn)程釋放以后,系統(tǒng)將會(huì)自動(dòng)將事件狀態(tài)復(fù)原為無(wú)信號(hào)狀態(tài)。
bInitialState:
[輸入]指定事件對(duì)象的初始狀態(tài)。如果為T(mén)RUE,初始狀態(tài)為有信號(hào)狀態(tài);否則為無(wú)信號(hào)狀態(tài)。
lpName:
[輸入]指定事件的對(duì)象的名稱(chēng),是一個(gè)以0結(jié)束的字符串指針。名稱(chēng)的字符格式限定在MAX_PATH之內(nèi)。名字是對(duì)大小寫(xiě)敏感的。
如果lpName指定的名字,與一個(gè)存在的命名的事件對(duì)象的名稱(chēng)相同,函數(shù)將請(qǐng)求EVENT_ALL_ACCESS來(lái)訪(fǎng)問(wèn)存在的對(duì)象。這時(shí)候,由于bManualReset和bInitialState參數(shù)已經(jīng)在創(chuàng)建事件的進(jìn)程中設(shè)置,這兩個(gè)參數(shù)將被忽略。如果lpEventAttributes是參數(shù)不是NULL,它將確定此句柄是否可以被繼承,但是其安全描述符成員將被忽略。
如果lpName為NULL,將創(chuàng)建一個(gè)無(wú)名的事件對(duì)象。
如果lpName的和一個(gè)存在的信號(hào)、互斥、等待計(jì)時(shí)器、作業(yè)或者是文件映射對(duì)象名稱(chēng)相同,函數(shù)將會(huì)失敗,在GetLastError函數(shù)中將返回ERROR_INVALID_HANDLE。造成這種現(xiàn)象的原因是這些對(duì)象共享同一個(gè)命名空間。
終端服務(wù)(Terminal Services):名稱(chēng)中可以加入"Global\"或是"Local\"的前綴,這樣可以明確的將對(duì)象創(chuàng)建在全局的或事務(wù)的命名空間。名稱(chēng)的其它部分除了反斜杠(\),可以使用任意字符。詳細(xì)內(nèi)容可參考Kernel Object Name Spaces。
Windows 2000:在Windows 2000系統(tǒng)中,沒(méi)有終端服務(wù)運(yùn)行,"Global\"和"Local\"前綴將被忽略。名稱(chēng)的其它部分除了反斜杠(\),可以使用任意字符。
Windows NT 4.0以及早期版本, Windows 95/98:名稱(chēng)中除了反斜杠(\),可以使用任意字符。
返回值:
如果函數(shù)調(diào)用成功,函數(shù)返回事件對(duì)象的句柄。如果對(duì)于命名的對(duì)象,在函數(shù)調(diào)用前已經(jīng)被創(chuàng)建,函數(shù)將返回存在的事件對(duì)象的句柄,而且在GetLastError函數(shù)中返回ERROR_ALREADY_EXISTS。
如果函數(shù)失敗,函數(shù)返回值為NULL,如果需要獲得詳細(xì)的錯(cuò)誤信息,需要調(diào)用GetLastError。
備注:
調(diào)用CreateEvent函數(shù)返回的句柄,該句柄具有EVENT_ALL_ACCESS權(quán)限去訪(fǎng)問(wèn)新的事件對(duì)象,同時(shí)它可以在任何有此事件對(duì)象句柄的函數(shù)中使用。
在調(diào)用的過(guò)程中,所有線(xiàn)程都可以在一個(gè)等待函數(shù)中指定事件對(duì)象句柄。當(dāng)指定的對(duì)象的狀態(tài)被置為有信號(hào)狀態(tài)時(shí),單對(duì)象等待函數(shù)將返回。
對(duì)于多對(duì)象等待函數(shù),可以指定為任意或所有指定的對(duì)象被置為有信號(hào)狀態(tài)。當(dāng)?shù)却瘮?shù)返回時(shí),等待線(xiàn)程將被釋放去繼續(xù)運(yùn)行。
初始狀態(tài)在bInitialState參數(shù)中進(jìn)行設(shè)置。使用SetEvent函數(shù)將事件對(duì)象的狀態(tài)置為有信號(hào)狀態(tài)。使用ResetEvent函數(shù)將事件對(duì)象的狀態(tài)置為無(wú)信號(hào)狀態(tài)。
當(dāng)一個(gè)手動(dòng)復(fù)原的事件對(duì)象的狀態(tài)被置為有信號(hào)狀態(tài)時(shí),該對(duì)象狀態(tài)將一直保持有信號(hào)狀態(tài),直至明確調(diào)用ResetEvent函數(shù)將其置為無(wú)符號(hào)狀態(tài)。
當(dāng)事件的對(duì)象被置為有信號(hào)狀態(tài)時(shí),任意數(shù)量的等待中線(xiàn)程,以及隨后開(kāi)始等待的線(xiàn)程均會(huì)被釋放。
當(dāng)一個(gè)自動(dòng)復(fù)原的事件對(duì)象的狀態(tài)被置為有信號(hào)狀態(tài)時(shí),該對(duì)象狀態(tài)將一直保持有信號(hào)狀態(tài),直至一個(gè)等待線(xiàn)程被釋放;系統(tǒng)將自動(dòng)將此函數(shù)置為無(wú)符號(hào)狀態(tài)。如果沒(méi)有等待線(xiàn)程正在等待,事件對(duì)象的狀態(tài)將保持有信號(hào)狀態(tài)。
多個(gè)進(jìn)程可持有同一個(gè)事件對(duì)象的多個(gè)句柄,可以通過(guò)使用此對(duì)象來(lái)實(shí)現(xiàn)進(jìn)程間的同步。下面的對(duì)象共享機(jī)制是可行的:
·在CreateEvent函數(shù)中,lpEventAttributes參數(shù)指定句柄可被繼承時(shí),通過(guò)CreateProcess函數(shù)創(chuàng)建的子進(jìn)程繼承的事件對(duì)象句柄。
·一個(gè)進(jìn)程可以在DuplicateHandle函數(shù)中指定事件對(duì)象句柄,從而獲得一個(gè)復(fù)制的句柄,此句柄可以被其它進(jìn)程使用。
·一個(gè)進(jìn)程可以在OpenEvent或CreateEvent函數(shù)中指定一個(gè)名字,從而獲得一個(gè)有名的事件對(duì)象句柄。
使用CloseHandle函數(shù)關(guān)閉句柄。當(dāng)進(jìn)程停止時(shí),系統(tǒng)將自動(dòng)關(guān)閉句柄。當(dāng)最后一個(gè)句柄被關(guān)閉后,事件對(duì)象將被銷(xiāo)毀。
使用環(huán)境:
Windows NT/2000:需要3.1或更高版本
Windows 95/98:需要Windows 95或更高版本
頭文件:定義在Winbase.h;需要包含 Windows.h。
導(dǎo)入庫(kù):user32.lib
Unicode:在Windows NT/2000中,以 Unicode 和 ANSI 執(zhí)行
一個(gè)Event被創(chuàng)建以后,可以用OpenEvent()API來(lái)獲得它的Handle,用CloseHandle()
來(lái)關(guān)閉它,用SetEvent()或PulseEvent()來(lái)設(shè)置它使其有信號(hào),用ResetEvent()
來(lái)使其無(wú)信號(hào),用WaitForSingleObject()或WaitForMultipleObjects()來(lái)等待
其變?yōu)橛行盘?hào).
PulseEvent()是一個(gè)比較有意思的使用方法,正如這個(gè)API的名字,它使一個(gè)Event
對(duì)象的狀態(tài)發(fā)生一次脈沖變化,從無(wú)信號(hào)變成有信號(hào)再變成無(wú)信號(hào),而整個(gè)操作是原子的.
對(duì)自動(dòng)復(fù)位的Event對(duì)象,它僅釋放第一個(gè)等到該事件的thread(如果有),而對(duì)于
人工復(fù)位的Event對(duì)象,它釋放所有等待的thread.
2.    WaitForSingleObject的用法
WaitForSingleObject的用法
DWORD WaitForSingleObject(
HANDLE hHandle,
DWORD dwMilliseconds
);
參數(shù)hHandle是一個(gè)事件的句柄,第二個(gè)參數(shù)dwMilliseconds是時(shí)間間隔。如果時(shí)間是有信號(hào)狀態(tài)返回WAIT_OBJECT_0,如果時(shí)間超過(guò)dwMilliseconds值但時(shí)間事件還是無(wú)信號(hào)狀態(tài)則返回WAIT_TIMEOUT。
hHandle可以是下列對(duì)象的句柄:
Change notification
Console input
Event
Job
Memory resource notification
Mutex
Process
Semaphore
Thread
Waitable timer
WaitForSingleObject函數(shù)用來(lái)檢測(cè)hHandle事件的信號(hào)狀態(tài),當(dāng)函數(shù)的執(zhí)行時(shí)間超過(guò)dwMilliseconds就返回,但如果參數(shù)dwMilliseconds為INFINITE時(shí)函數(shù)將直到相應(yīng)時(shí)間事件變成有信號(hào)狀態(tài)才返回,否則就一直等待下去,直到WaitForSingleObject有返回直才執(zhí)行后面的代碼。在這里舉個(gè)例子:
先創(chuàng)建一個(gè)全局Event對(duì)象g_event:
CEvent g_event;
在程序中可以通過(guò)調(diào)用CEvent::SetEvent設(shè)置事件為有信號(hào)狀態(tài)。
下面是一個(gè)線(xiàn)程函數(shù)MyThreadPro()
UINT CFlushDlg::MyThreadProc( LPVOID pParam )
{
WaitForSingleObject(g_event,INFINITE);
For(;;)
{
………….
}
return 0;
}
在這個(gè)線(xiàn)程函數(shù)中只有設(shè)置g_event為有信號(hào)狀態(tài)時(shí)才執(zhí)行下面的for循環(huán),因?yàn)間_event是全局變量,所以我們可以在別的線(xiàn)程中通過(guò)g_event. SetEvent控制這個(gè)線(xiàn)程。
還有一種用法就是我們可以通過(guò)WaitForSingleObject函數(shù)來(lái)間隔的執(zhí)行一個(gè)線(xiàn)程函數(shù)的函數(shù)體
UINT CFlushDlg::MyThreadProc( LPVOID pParam )
{
while(WaitForSingleObject(g_event,MT_INTERVAL)!=WAIT_OBJECT_0)
{
………………
}
return 0;
}
在這個(gè)線(xiàn)程函數(shù)中可以可以通過(guò)設(shè)置MT_INTERVAL來(lái)控制這個(gè)線(xiàn)程的函數(shù)體多久執(zhí)行一次,當(dāng)事件為無(wú)信號(hào)狀態(tài)時(shí)函數(shù)體隔MT_INTERVAL執(zhí)行一次,當(dāng)設(shè)置事件為有信號(hào)狀態(tài)時(shí),線(xiàn)程就執(zhí)行完畢了(return 0)。
本站僅提供存儲(chǔ)服務(wù),所有內(nèi)容均由用戶(hù)發(fā)布,如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊舉報(bào)。
打開(kāi)APP,閱讀全文并永久保存 查看更多類(lèi)似文章
猜你喜歡
類(lèi)似文章
VC 線(xiàn)程間通信
CreateEvent的用法
CreateEvent的使用方法學(xué)習(xí)
CEvent類(lèi)及常用函數(shù)
線(xiàn)程、線(xiàn)程句柄、線(xiàn)程ID
WaitForSingleObjet
更多類(lèi)似文章 >>
生活服務(wù)
分享 收藏 導(dǎo)長(zhǎng)圖 關(guān)注 下載文章
綁定賬號(hào)成功
后續(xù)可登錄賬號(hào)暢享VIP特權(quán)!
如果VIP功能使用有故障,
可點(diǎn)擊這里聯(lián)系客服!

聯(lián)系客服