《C#多线程编程实战》2.9 ReaderWirterLockSlim

可以多线程进行读写操作。

比如书上的示例代码是三个线程进行读取,两个线程进行写入工作。

如果 用之前学过的也不是不可以用,但是用的有些多。

所有ReaderWirterLockSlim专门为此而来。

读取锁。

注意的地方,

三种方式

EnterReadLock//确认进行读取

EnterWriteLock//确认进行写入

EnterUpgradeableReadLock//确认升级读取锁

前两个很明显,是对应两种模式。

那第三种呢?

在写入之前是要获取写入锁,而这个写入锁会锁定其他线程的读取,写入。也就是会极大导致读取的操作的线程工作速率。

此时可以使用升级读取锁,先读,在这个过程中在进行写入工作。

不过要主要的是,一定要写好退出的语句,也就是下面这个三个

ExitReadLock

ExitWriteLock

ExitUpgradeableReadLock

它们是成对出现的。

而且最好是使用Try Finally的方式

class Program
    {
        static void Main(string[] args)
        {
            new Thread(Read){ IsBackground = true }.Start();
            new Thread(Read){ IsBackground = true }.Start();
            new Thread(Read){ IsBackground = true }.Start();

            new Thread(() => Write("Thread 1")){ IsBackground = true }.Start();
            new Thread(() => Write("Thread 2")){ IsBackground = true }.Start();

            Sleep(TimeSpan.FromSeconds(30));
            Console.ReadKey();
        }

        static ReaderWriterLockSlim _rw = new ReaderWriterLockSlim();
        static Dictionary<int, int> _items = new Dictionary<int, int>();

        static void Read()
        {
            
            WriteLine("Reading contents of a dictionary");
            while (true)
            {
                try
                {
                    _rw.EnterReadLock();
                    foreach (var key in _items.Keys)
                    {
                        Sleep(TimeSpan.FromSeconds(0.1));
                    }
                }
                finally
                {
                    _rw.ExitReadLock();
                }
            }
        }

        static void Write(string threadName)
        {
            while (true)
            {
                try
                {
                    int newKey = new Random().Next(250);
                    _rw.EnterUpgradeableReadLock();
                    if (!_items.ContainsKey(newKey))
                    {
                        try
                        {
                            _rw.EnterWriteLock();
                            _items[newKey] = 1;
                            WriteLine($"New key {newKey} is added to a dictionary by a {threadName}");
                        }
                        finally
                        {
                            _rw.ExitWriteLock();
                        }
                    }
                    Sleep(TimeSpan.FromSeconds(0.1));
                }
                finally
                {
                    _rw.ExitUpgradeableReadLock();
                }
            }
        }
    }

 

posted @ 2018-08-08 14:29  ARM830  阅读(280)  评论(0编辑  收藏  举报