基於windows api實現的共用鎖定/獨佔鎖

來源:互聯網
上載者:User

標籤:情況   pac   close   讀取   int   windows平台   oid   ftps   struct   

眾所周知,windows平台上實現線程同步。或者說資源的加鎖與解鎖的方法有核心事件、臨界區、相互排斥量、訊號量,甚至interlocked系列函數等多種手段。

可是在日常的編程中,我們使用這些手段對 “多個線程同一時候對同一個資源進行讀寫”的時候,在讀寫之前先要對資源假鎖,讀寫完之後要對資源解鎖。

設想這樣一種情況,有一個ftpserver。每天有非常頻繁的對這個ftp服務的檔案進行下載,可是差點兒好幾天才會對這些檔案進行更新。在我們每一次對檔案下載的時候,讀取檔案的時候都要對檔案進行加鎖,以保證同一時候沒有其它人對檔案進行寫入。

可是這些加鎖的行為。在99%的時候都是不會有人同一時候寫入檔案的。僅僅有1%的情況下會有人同一時候也要寫入檔案。這種話,我們多鎖就大大的浪費了,並且你在加鎖的同一時候,別人即使也僅僅是讀取檔案,也須要等你先解鎖。


解決問題的辦法是,對檔案的讀取設定共用鎖定。多個線程能夠同一時候讀檔案。不會互相堵塞。再設定獨佔鎖,當要對檔案進行寫入的時候。加上獨佔鎖,這樣別的線程此時不能讀也不能寫。


windows提供了一個稱為slim 的共用/獨佔鎖來解決問題。可是呢。slim僅僅在vista和window server 2008才支援。在之前的版本號碼上沒有支援。

於是,我就w利用現有的線程同步手段,來類比達到slim這一個共用/獨佔鎖的功能,代碼封裝例如以下:



</pre><pre name="code" class="cpp">//共用和獨佔鎖(讀不鎖。寫鎖),適用於資源的讀的頻率比寫的頻率高的情況//共用鎖定: 大家都能夠同一時候讀,可是不能寫。//獨佔鎖: 就是僅僅有一個人獨佔使用,無論是讀還是寫//規定:acquire和release必須成對出現。不支援嵌套以及互相嵌套//缺點:須要對加鎖過程本身進行臨界區控制。會帶來細微的效能損失#ifdef __cplusplusextern "C" {#endifstruct SELock //Shared & Exclusive lock{       RTL_CRITICAL_SECTION sec_shared,sec_exclusive; //對加鎖代碼本身進行臨界區控制    HANDLE exclusive_evt;    HANDLE shared_evt;    volatile long shared_count;};//初始化一個SE鎖_inline void InitializeSELock(SELock *lock){    InitializeCriticalSection(&lock->sec_shared);    InitializeCriticalSection(&lock->sec_exclusive);    lock->exclusive_evt = CreateEventW(NULL,TRUE,TRUE,NULL);    lock->shared_evt = CreateEventW(NULL,TRUE,TRUE,NULL);    lock->shared_count = 0;}//清理一個SE鎖_inline void DeleteSELock(SELock *lock){        DeleteCriticalSection(&lock->sec_shared);    DeleteCriticalSection(&lock->sec_exclusive);    CloseHandle(lock->exclusive_evt);    CloseHandle(lock->shared_evt);    lock->shared_count = 0;}//請求共用鎖定,用於讀_inline void AcquireSELockShared(SELock *lock){    EnterCriticalSection(&lock->sec_exclusive);       EnterCriticalSection(&lock->sec_shared);         WaitForSingleObject(lock->exclusive_evt,INFINITE); //等待獨佔鎖        ++lock->shared_count;    if(lock->shared_count)        ResetEvent(lock->shared_evt); //開啟共用鎖定          LeaveCriticalSection(&lock->sec_shared);    LeaveCriticalSection(&lock->sec_exclusive);}//釋放共用鎖定_inline void ReleaseSELockShared(SELock *lock){    EnterCriticalSection(&lock->sec_shared);        --lock->shared_count;        if(!lock->shared_count)        SetEvent(lock->shared_evt); //關閉共用鎖定            LeaveCriticalSection(&lock->sec_shared);    }//請求獨佔鎖_inline void AcquireSELockExclusive(SELock *lock){    EnterCriticalSection(&lock->sec_exclusive);        WaitForSingleObject(lock->exclusive_evt,INFINITE); //等待獨佔鎖    WaitForSingleObject(lock->shared_evt,INFINITE); //等待共用鎖定    ResetEvent(lock->exclusive_evt); //開啟獨佔鎖    LeaveCriticalSection(&lock->sec_exclusive);}//釋放獨佔鎖_inline void ReleaseSELockExclusive(SELock *lock){    SetEvent(lock->exclusive_evt); //關閉獨佔鎖}#ifdef __cplusplus}#endif


基於windows api實現的共用鎖定/獨佔鎖

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.