[C#]Thread Safe Dictionary in .NET 2.0

using System.Collections.Generic;
using System.Threading;

namespace CSharpUtilHelpV2
{
    /// <summary>
    /// 基于.NET 2.0的对于Dictionary线程安全操作工具类
    /// 说明
    /// 默认读锁超时1000毫秒
    /// 默认写锁超时1000毫秒
    /// .NET 4.0 可以使用ConcurrentDictionary来实现。
    /// </summary>
    /// <typeparam name="T">泛型</typeparam>
    public class ThreadSafeDictionaryV2<T>
    {
        /*参考资料
         * 1.
         * 使用Monitor或Mutex进行同步控制的问题:由于独占访问模型不允许任何形式的并发访问,这样的效率总是不太高。
         * 许多时候,应用程序在访问资源时是进行读操作,写操作相对较少。为解决这一问题,
         * C#提供了System.Threading.ReaderWriterLock类以适应多用户读/单用户写的场景。该类可实现以下功能:
         * 如果资源未被写操作锁定,那么任何线程都可对该资源进行读操作锁定,并且对读操作锁数量没有限制,即多个线程可同时对该资源进行读操作锁定,以读取数据。
         * 如果资源未被添加任何读或写操作锁,那么一个且仅有一个线程可对该资源添加写操作锁定,以写入数据。简单的讲就是:读操作锁是共享锁,允许多个线程同时读取数据;
         * 写操作锁是独占锁,同一时刻,仅允许一个线程进行写操作。
         * 引用链接:http://www.csharpwin.com/dotnetspace/12761r5814.shtml
         *
         * 2.
         * ReaderWriterLock 用于同步对资源的访问。在任一特定时刻,它允许多个线程同时进行读访问,或者允许单个线程进行写访问。
         * 在资源不经常发生更改的情况下,ReaderWriterLock 所提供的吞吐量比简单的一次只允许一个线程的锁(如 Monitor)更高。
         * 在多数访问为读访问,而写访问频率较低、持续时间也比较短的情况下,ReaderWriterLock 的性能最好。
         * 多个读线程与单个写线程交替进行操作,所以读线程和写线程都不会长时间阻止。
         * 大多数在 ReaderWriterLock 上获取锁的方法都采用超时值。使用超时可以避免应用程序中出现死锁。
         * 如果不使用超时,这两个线程将出现死锁。
         * 引用链接: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;//默认读锁超时1000毫秒
        static int writerTimeout = 1000;//默认写锁超时1000毫秒
        /// <summary>
        /// 默认构造函数
        /// </summary>
        public ThreadSafeDictionaryV2()
        {

        }
        /// <summary>
        /// 带参构造函数
        /// </summary>
        /// <param name="_readerTimeout">读锁超时设置【单位毫秒】</param>
        /// <param name="_writerTimeout">写锁超时设置【单位毫秒】</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【线程安全】
        /// 默认超时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">超时设置【毫秒】</param>
        public void Add(string key, T val, int timeout)
        {
            rwlock.AcquireWriterLock(timeout);
            try
            {
                dic[key] = val;
            }
            finally
            {
                rwlock.ReleaseWriterLock();
            }
        }
        /// <summary>
        /// Get【线程安全】
        /// 默认超时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">超时设置【毫秒】</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【线程安全】
        /// 默认超时1000毫秒
        /// </summary>
        /// <param name="key">键</param>
        public void Remove(string key)
        {
            Remove(key, writerTimeout);
        }
        /// <summary>
        /// Remove【线程安全】
        /// </summary>
        /// <param name="key">键</param>
        /// <param name="timeout">超时设置【毫秒】</param>
        public void Remove(string key, int timeout)
        {
            rwlock.AcquireWriterLock(timeout);
            try
            {
                dic.Remove(key);
            }
            finally
            {
                rwlock.ReleaseWriterLock();
            }
        }
        /// <summary>
        /// Clear【线程安全】
        /// 默认超时1000毫秒
        /// </summary>
        public void Clear()
        {
            Clear(writerTimeout);
        }
        /// <summary>
        /// Clear【线程安全】
        /// </summary>
        /// <param name="timeout">超时设置【毫秒】</param>
        public void Clear(int timeout)
        {
            rwlock.AcquireWriterLock(timeout);
            try
            {
                dic.Clear();
            }
            finally
            {
                rwlock.ReleaseWriterLock();
            }
        }
        /// <summary>
        /// ContainsKey【线程安全】
        /// 默认超时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">超时设置【毫秒】</param>
        /// <returns>是否包含</returns>
        public bool ContainsKey(string key, int timeout)
        {
            rwlock.AcquireReaderLock(timeout);
            try
            {
                return dic.ContainsKey(key);
            }
            finally
            {
                rwlock.ReleaseReaderLock();
            }
        }
        /// <summary>
        /// Count【线程安全】
        /// 默认超时1000毫秒
        /// </summary>
        /// <returns></returns>
        public int Count()
        {
            return Count(readerTimeout);
        }
        /// <summary>
        /// Count【线程安全】
        /// </summary>
        /// <param name="timeout">超时设置【毫秒】</param>
        /// <returns>Count</returns>
        public int Count(int timeout)
        {
            rwlock.AcquireReaderLock(timeout);
            try
            {
                return dic.Count;
            }
            finally
            {
                rwlock.ReleaseReaderLock();
            }
        }
    }
}

.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

[C#]Thread Safe Dictionary in .NET 2.0

时间: 2024-10-24 22:42:23

[C#]Thread Safe Dictionary in .NET 2.0的相关文章

PHP Thread Safe和Non ThreadSafe

原文地址 http://blog.csdn.net/lrcoop/article/details/45477371 如何选择Thread Safe和Non ThreadSafe版本? Windows版的PHP从版本5.2.1开始有ThreadSafe(线程安全)和None Thread Safe(NTS,非线程安全)之分,这两者不同在于何处?到底应该用哪种?这里做一个简单的介绍. 从2000年10月20日发布的第一个Windows版的PHP3.0.17开始的都是线程安全的版本,这是由于与linu

php Thread Safe(线程安全)与None Thread Safe(NTS,非线程安全)之分

Windows版的PHP从版本5.2.1开始有Thread Safe(线程安全)和None Thread Safe(NTS,非线程安全)之分,这两者不同在于何处?到底应该用哪种?这里做一个简单的介绍. 从2000年10月20日发布的第一个Windows版的PHP3.0.17开始的都是线程安全的版本,这是由于与Linux/Unix系统是采用多进程的工作方式不同的是Windows系统是采用多线程的工作方式.如果在IIS下以CGI方式运行PHP会非常慢,这是由于CGI模式是建立在多进程的基础之上的,而

PHP版本VC6与VC9、Thread Safe与None-Thread Safe等的区别

最近发现很多PHP程序员对PHP版本知识了解不是很清楚,自己也看了不少类似的文章,还是感觉不够明确和全面,网上的结论又都是模棱两可,在此,给出最完整甚至武断的解释. 本文讲解:VC6与VC9,Thread Safety与None-Thread Safe,Apache module与fastcgi的区别与选择. PHP的大版本主要分三支:PHP4/PHP5/PHP6 其中,PHP4由于太古老.对OO支持不力已基本被淘汰,请无视PHP4. PHP6由于基本没有生产线上的应用,还基本只是一款概念产品,

PHP版本VC6与VC9/VC11/VC14、Thread Safe与None-Thread Safe等的区别

最近正好在弄一个PHP的程序,在这之前一直没有怎么以接触,发现对PHP版本知识了解不是很清楚,自己看了不少类似的文章,还是感觉不够明确和全面, 网上的结论又都是模棱两可,在此,给出最完整甚至武断的解释.(内面部分内容是摘自其它程序员的博文) 本文讲解:VC6与VC9,Thread Safety与None-Thread Safe,Apache module与fastcgi的区别与选择. PHP的大版本主要分支:PHP4/PHP5/PHP7(PHP6官方没有) 其中,PHP4由于太古老.对OO支持不

Thread Safe(线程安全)和None Thread Safe(NTS,非线程安全)之分

Windows版的PHP从版本5.2.1开始有Thread Safe(线程安全)和None Thread Safe(NTS,非线程安全)之分,这两者不同在于何处?到底应该用哪种?这里做一个简单的介绍. 从2000年10月20日发布的第一个Windows版的PHP3.0.17开始的都是线程安全的版本,这是由于与Linux/Unix系统是采用多进程的工作方式不同的是Windows系统是采用多线程的工作方式.如果在IIS下以CGI方式运行PHP会非常慢,这是由于CGI模式是建立在多进程的基础之上的,而

PHP关于VC11,VC9,VC6以及Thread Safe和Non Thread Safe版本选择的问题

现在PHP官网上下载PHP安装包都有VC11或VC9的字样,这是什么含义,我们应该下载哪种安装包更好呢? 其实PHP官网给出了答案: VC6版本是使用Visual Studio 6编译器编译的,如果你的PHP是用Apache来架设的,那你就选择VC6版本.(现在PHP已经没有VC6了). VC9意思就是该版本PHP是用VisualStudio2008编译的,而VC11则是用VisualStudio2012编译的. 如果你下载的是VC9版本的,就需要先安VisualC++Redistributab

PHP5.3中关于VC9和VC6以及Thread Safe和Non Thread Safe版本选择的问题

转自:http://www.htmer.com/article/716.htm 最近在PHP官网上看到又有新版的PHP下载了,于是上去找找For Windows的版本,可是一看确傻眼了,一共给了四个版本,VC9 x86 Non Thread Safe.VC9 x86 Thread Safe.VC6 x86 Non Thread Safe.VC6 x86 Thread Safe,这让我这个菜鸟头疼啊,还好PHP官网提供下载的地方左边有个英文choose我看懂了,我估摸着就是如何来选择版本的意思吧,

Windows下PHP(Thread Safe与Non Thread Safe)版本说明

转载"http://www.taoz11.com/archives/300.html" linux下直接下载源码,在服务器上编译即可,发现windows下有4个版本: VC9 x86 Non Thread SafeVC9 x86 Thread SafeVC6 x86 Non Thread SafeVC6 x86 Thread Safe 网上查看了下4种版本对应使用的情况 一.如何选择 php5.3 的 VC9 版本和 VC6 版本VC6 版本是使用 Visual Studio 6 编译

PHP的 ISAPI和FastCGI运行如何选择Thread Safe与Non Thread Safe

php版本越来越多,难免有版本选择的疑惑. VC9的版本是用legacy VS 2008编译的, VC6的版本是用legacy VS6编译的. 如果你是在windows下使用IIS+PHP的话,你需要下载VC9的版本. 如果你是在windows下使用Apache+PHP的话,你需要下载VC6的版本. nts(Non Thread Safe)是指非线程安全,ts(Thread Safe)则是指线程安全. PHP有2中运行方式:ISAPI和FastCGI. ISAPI执行方式是以DLL动态库的形式使