using System.Collections.Generic;using System.Threading;namespace CSharpUtilHelpV2{ /// <summary> /// 基于.NET 2.0的對(duì)于Dictionary線程安全操作工具類 /// 說(shuō)明 /// 默認(rèn)讀鎖超時(shí)1000毫秒 /// 默認(rèn)寫鎖超時(shí)1000毫秒 /// .NET 4.0 可以使用ConcurrentDictionary來(lái)實(shí)現(xiàn)。 /// </summary> /// <typeparam name="T">泛型</typeparam> public class ThreadSafeDictionaryV2<T> { /*參考資料 * 1. * 使用Monitor或Mutex進(jìn)行同步控制的問(wèn)題:由于獨(dú)占訪問(wèn)模型不允許任何形式的并發(fā)訪問(wèn),這樣的效率總是不太高。 * 許多時(shí)候,應(yīng)用程序在訪問(wèn)資源時(shí)是進(jìn)行讀操作,寫操作相對(duì)較少。為解決這一問(wèn)題, * C#提供了System.Threading.ReaderWriterLock類以適應(yīng)多用戶讀/單用戶寫的場(chǎng)景。該類可實(shí)現(xiàn)以下功能: * 如果資源未被寫操作鎖定,那么任何線程都可對(duì)該資源進(jìn)行讀操作鎖定,并且對(duì)讀操作鎖數(shù)量沒(méi)有限制,即多個(gè)線程可同時(shí)對(duì)該資源進(jìn)行讀操作鎖定,以讀取數(shù)據(jù)。 * 如果資源未被添加任何讀或?qū)懖僮麈i,那么一個(gè)且僅有一個(gè)線程可對(duì)該資源添加寫操作鎖定,以寫入數(shù)據(jù)。簡(jiǎn)單的講就是:讀操作鎖是共享鎖,允許多個(gè)線程同時(shí)讀取數(shù)據(jù); * 寫操作鎖是獨(dú)占鎖,同一時(shí)刻,僅允許一個(gè)線程進(jìn)行寫操作。 * 引用鏈接:http://www.csharpwin.com/dotnetspace/12761r5814.shtml * * 2. * ReaderWriterLock 用于同步對(duì)資源的訪問(wèn)。在任一特定時(shí)刻,它允許多個(gè)線程同時(shí)進(jìn)行讀訪問(wèn),或者允許單個(gè)線程進(jìn)行寫訪問(wèn)。 * 在資源不經(jīng)常發(fā)生更改的情況下,ReaderWriterLock 所提供的吞吐量比簡(jiǎn)單的一次只允許一個(gè)線程的鎖(如 Monitor)更高。 * 在多數(shù)訪問(wèn)為讀訪問(wèn),而寫訪問(wèn)頻率較低、持續(xù)時(shí)間也比較短的情況下,ReaderWriterLock 的性能最好。 * 多個(gè)讀線程與單個(gè)寫線程交替進(jìn)行操作,所以讀線程和寫線程都不會(huì)長(zhǎng)時(shí)間阻止。 * 大多數(shù)在 ReaderWriterLock 上獲取鎖的方法都采用超時(shí)值。使用超時(shí)可以避免應(yīng)用程序中出現(xiàn)死鎖。 * 如果不使用超時(shí),這兩個(gè)線程將出現(xiàn)死鎖。 * 引用鏈接:http://msdn.microsoft.com/zh-cn/library/system.threading.readerwriterlock(v=vs.80).aspx * * 3.其他鏈接 * http://tinythreadsafecache.codeplex.com/SourceControl/latest#TinyThreadSafeCache.cs * http://www.grumpydev.com/2010/02/25/thread-safe-dictionarytkeytvalue/ * http://stackoverflow.com/questions/157933/whats-the-best-way-of-implementing-a-thread-safe-dictionary * http://stackoverflow.com/questions/15095817/adding-to-a-generic-dictionary-causes-indexoutofrangeexception */ ReaderWriterLock rwlock = new ReaderWriterLock();//聲明讀寫鎖 .NET 3.5+ 推薦用ReaderWriterLockSlim Dictionary<string, T> dic = new Dictionary<string, T>();//Dictionary static int readerTimeout = 1000;//默認(rèn)讀鎖超時(shí)1000毫秒 static int writerTimeout = 1000;//默認(rèn)寫鎖超時(shí)1000毫秒 /// <summary> /// 默認(rèn)構(gòu)造函數(shù) /// </summary> public ThreadSafeDictionaryV2() { } /// <summary> /// 帶參構(gòu)造函數(shù) /// </summary> /// <param name="_readerTimeout">讀鎖超時(shí)設(shè)置【單位毫秒】</param> /// <param name="_writerTimeout">寫鎖超時(shí)設(shè)置【單位毫秒】</param> public ThreadSafeDictionaryV2(int _readerTimeout, int _writerTimeout) { readerTimeout = _readerTimeout; writerTimeout = _writerTimeout; } /// <summary> /// This【線程安全】 /// </summary> /// <param name="key">鍵</param> /// <returns>值</returns> public T this[string key] { get { rwlock.AcquireReaderLock(readerTimeout); try { return dic[key]; } finally { rwlock.ReleaseReaderLock(); } } set { rwlock.AcquireWriterLock(writerTimeout); try { dic[key] = value; } finally { rwlock.ReleaseWriterLock(); } } } /// <summary> /// Add【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> /// <param name="key">鍵</param> /// <param name="val">值</param> public void Add(string key, T val) { Add(key, val, writerTimeout); } /// <summary> /// Add【線程安全】 /// </summary> /// <param name="key">鍵</param> /// <param name="val">值</param> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> public void Add(string key, T val, int timeout) { rwlock.AcquireWriterLock(timeout); try { dic[key] = val; } finally { rwlock.ReleaseWriterLock(); } } /// <summary> /// Get【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> /// <param name="key">鍵</param> /// <returns>值</returns> public T Get(string key) { return Get(key, readerTimeout); } /// <summary> /// Get【線程安全】 /// </summary> /// <param name="key">鍵</param> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> /// <returns>值</returns> public T Get(string key, int timeout) { rwlock.AcquireReaderLock(timeout); try { T val; dic.TryGetValue(key, out val); return val; } finally { rwlock.ReleaseReaderLock(); } } /// <summary> /// Remove【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> /// <param name="key">鍵</param> public void Remove(string key) { Remove(key, writerTimeout); } /// <summary> /// Remove【線程安全】 /// </summary> /// <param name="key">鍵</param> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> public void Remove(string key, int timeout) { rwlock.AcquireWriterLock(timeout); try { dic.Remove(key); } finally { rwlock.ReleaseWriterLock(); } } /// <summary> /// Clear【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> public void Clear() { Clear(writerTimeout); } /// <summary> /// Clear【線程安全】 /// </summary> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> public void Clear(int timeout) { rwlock.AcquireWriterLock(timeout); try { dic.Clear(); } finally { rwlock.ReleaseWriterLock(); } } /// <summary> /// ContainsKey【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> /// <param name="key">鍵</param> /// <returns>是否包含</returns> public bool ContainsKey(string key) { return ContainsKey(key, readerTimeout); } /// <summary> /// ContainsKey【線程安全】 /// </summary> /// <param name="key">鍵</param> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> /// <returns>是否包含</returns> public bool ContainsKey(string key, int timeout) { rwlock.AcquireReaderLock(timeout); try { return dic.ContainsKey(key); } finally { rwlock.ReleaseReaderLock(); } } /// <summary> /// Count【線程安全】 /// 默認(rèn)超時(shí)1000毫秒 /// </summary> /// <returns></returns> public int Count() { return Count(readerTimeout); } /// <summary> /// Count【線程安全】 /// </summary> /// <param name="timeout">超時(shí)設(shè)置【毫秒】</param> /// <returns>Count</returns> public int Count(int timeout) { rwlock.AcquireReaderLock(timeout); try { return dic.Count; } finally { rwlock.ReleaseR
新聞熱點(diǎn)
疑難解答
圖片精選
網(wǎng)友關(guān)注