實現乙個Semaphore

2021-04-19 07:23:11 字數 1376 閱讀 2465

其實這是我boss的想法,我一開始聽他這麼說也覺得比較差異,ms已經寫好了何必再自己寫乙個.答案有兩個:1ms寫的東西未必就是最好的,如完成埠,heap等.2semaphore是多執行緒程式設計中的核心元素所以有必要提速.我們都知道在多執行緒中ms提供的多個現成阻塞核心物件中critical(monitor),mutex,semaphore,event(eventwaithandle),event的代價是最小的,所以我們就選擇用event來實現semaphore.

event是乙個不完整的semaphore,它不能連續喚醒多個阻塞的執行緒.而為了能夠自動的,連續的喚醒阻塞的執行緒,我想到了半自動步槍的發射原理:當槍膛中的一顆子彈發射後由於後座力會使槍機在自動的從彈夾中壓入乙個子彈進入槍膛.將這個想法運用到這裡就是:當乙個執行緒被喚醒後就相當於打出一顆子彈,它需要再激發一次event已達到自動壓子彈的目的.

當然僅使用event是不夠的,因為還要處理槍膛裡是否有子彈和當前子彈數這兩個臨界條件.而為了提高效能我們不能使用普通的鎖(critical或mutex)還有乙個原因是我說過semaphore是多執行緒程式設計中最核心的元素,鎖就應該用它來實現.因此在這裡我們選擇使用interlocked(內鎖,它的效能很高在納秒級別.通過降低控制粒度可以很好的提高併發程式的效率)實際上在這個設計中event只是為了讓執行緒阻塞用的,而這兩個臨界條件才是關鍵.

下面進入**部分: 我們需要三個成員變數,是否可以**(槍膛中是否有子彈),子彈數和押子彈

int _canfire;                       //這裡不用bool是因為 interlocked.exchange方法不接受bool型別

long _bulletcount;                   

eventwaithandle _clipbullet;

public semaphore() : this(0)

public semaphore(int size)      //我認為semaphore的最大可用數為無限

private void loadbullet()           //子彈上膛

public void release()

public void release(int count)

public bool waitone()

if (atomic.decrement(ref this._bulletcount) > 0)  //如果還有子彈則自動壓入一顆

this.loadbullet();

return true;

}public bool try_wait()   //嘗試等待,相當於waitone(0) 這是乙個很常用的功能所以要單獨處理

在c++環境下測試比windows原始semaphore快將近2被,在.net下沒有明顯效果.我覺得這和虛機的排程實現有關係.

使用semaphore寫乙個顯示鎖

這裡只是將semaphore包裝了一下,注意當semaphore的構造引數是1時,本身就是乙個顯示鎖 public class semaphorelock public void unlock public static void main string args catch interrupted...

乙個Redis Cache實現

應用中需要通過http呼叫遠端的資料,但是這個獲取過程需要執行較長時間,而且這個資料本身的變化也不頻繁,這種情況最適合用乙個cache來優化。前兩年在做短鏈結實現的時候,曾經用最好的語言php做過乙個redis cache實現 乙個簡單的redis應用 修訂版 但那個畢竟是乙個特定的實現,而且我現在...

實現乙個call

call是js最好用的函式之一,改變函式上下文是外掛程式編寫最經常使用的特性。var name 小鋼炮 var cat function say name say ketty 小鋼炮 ketty say.call cat,ketty 貓 ketty看下面 function say name var ...