1. 程式人生 > >C++在Windows環境下多執行緒自動鎖的實現

C++在Windows環境下多執行緒自動鎖的實現

                         許久不更博了,手有點生了………… 博主最近找工作並實習去了,忙碌的生活也算比較充實,      然後就是擠不出時間來更博真是尷尬尷尬啊…………尷尬

                                          在實習期間的主要任務就是看程式碼,瞭解程式碼流程、根據程式碼流程實現新的功能,坑爹的是代

     碼裡面的註釋好少好少啊…… 真是辛酸,也是適應了一段時間。

             一開始博主看的是伺服器端的程式碼(windows下的伺服器程式碼),在看程式碼的過程中看到了          CAutolock這個玩意~ 今天我就是來講這個玩意是怎麼實現的。

             顧名思義CAutolock就是自動鎖的意思,它可以把它之下的程式碼區鎖住一直到其自身被釋放掉

   後這塊程式碼區中的公共資源才會被其他執行緒使用。當然這個程式碼區能儘量少就儘量少,畢竟不能讓其他線

   程這樣一直等下去反而降低了效率。

             CAutolock是一個類,要知道它的工作原理就要深度剖析它的內部內容。

             首先介紹它的最基礎內容:CRITICAL_SECTION.

             CRITICAL_SECTION是一個結構體,它在windows.h檔案中被定義,它是臨界區的意思。就像

   多個執行緒公共訪問的資源一樣,主要和它涉及相關的四個函式分別是:

             InitializeCriticalSection(CRITICAL_SECTION* para) 初始化CRITICAL_SECTION

             EnterCriticalSection(CRITICAL_SECTION* para)  進入CRITICAL_SECTION

             LeaveCriticalSection(CRITICAL_SECTION* para)  離開CRITICAL_SECTION

             DeleteCriticalSection(CRITICAL_SECTION* para)  刪除CRITICAL_SECTION

             其實單獨使用它就可以實現鎖,例如:

             CRITICAL_SECTION para;

             InitializeCriticalSection(&para);

             EnterCriticalSection(&para);

             ………………

             LeaveCriticalSection(&para);

             DeleteCriticalSection(&para);

             這樣EnterCriticalSection和LeaveCriticalSection之間的程式碼區就被鎖住了~ 這裡面的

    公共資源其他執行緒就訪問不到了。

             但是這樣又會很麻煩,在每個用到公共資源的地方都要成套的把這段程式碼貼上去很明顯影響

    了效率,所以就對它進行了封裝生成了CAutolock類~  接下來先看下第一層封裝吧!

<span style="font-size:14px;">class CCritSec
{
public:
	CRITICAL_SECTION csec;
	CCritSec()
	{
		InitializeCriticalSection(&csec);
	}
	~CCritSec()
	{
		DeleteCriticalSection(&csec);
	}
	

	void lock()
	{
		EnterCriticalSection(&csec);
	}

	void unlock()
	{
		LeaveCriticalSection(&csec);
	}
};</span>

                  CCritSec類中建構函式對成員變數csec進行初始化,相應的解構函式中對csec進行刪除,另外還    封裝了lock和unlock函式去執行EnterCriticalSection和LeaveCriticalSection。

           對CAutolock的封裝就比較簡單了:

<span style="font-size:14px;">class CAutolock
{
public:
	CCritSec* csec;
	CAutolock(CCritSec* critsec)
	{
		csec = critsec;
		csec->lock();
	}
	~CAutolock()
	{
		csec->unlock();
	}
};</span>
 

                   這樣下來自動鎖的封裝就完成了~  至於使用它,我們只需要定義一個CCritSec變數,然後再用

    CAutolock,這樣知道CAutolock被析構之前的程式碼區都會被鎖住。

           如果我們要鎖住的程式碼區在中間的話我們也可以使用程式塊的( {…………} )原理,將臨界區包

    起來在程式塊中定義CAutolock,當代碼執行出程式塊時CAutolock自動會被析構掉,這樣這個程式塊內

    的程式碼就會被鎖住也不會影響其他程式碼的執行。