简体   繁体   English

AutoResetEvent作为C#中的Lock替换?

[英]AutoResetEvent as a Lock replacement in C#?

I was wondering: Locking allows only 1 thread to enter a code region 我想知道:锁定只允许1个线程进入代码区域

And wait handles is for signaling : : 等待句柄用于发信号:

Signaling is when one thread waits until it receives notification from another. 信令是指一个线程等待它收到另一个线程的通知。

So I thought to myself , can this be used to replace a lock ? 所以我心想,这可以用来取代锁吗?

something like : 就像是 :

Thread number 1 --please enter ( autoreset --> autlock)
dowork...
finish work...
set signal  to invite the next thread

So I wrote this : 所以我写了这个:

/*1*/   static EventWaitHandle _waitHandle = new AutoResetEvent(true);
/*2*/   
/*3*/   volatile int i = 0;
/*4*/   void Main()
/*5*/   {
/*6*/   
/*7*/       for (int k = 0; k < 10; k++)
/*8*/       {
/*9*/           var g = i;
/*10*/           Interlocked.Increment(ref i);
/*11*/           new Thread(() = > DoWork(g)).Start();
/*12*/   
/*13*/       }
/*14*/   
/*15*/       Console.ReadLine();
/*16*/   }
/*17*/   
/*18*/   
/*19*/   void DoWork(object o)
/*20*/   {
/*21*/       _waitHandle.WaitOne();
/*22*/       Thread.Sleep(10);
/*23*/       Console.WriteLine((int) o + "Working...");
/*24*/       _waitHandle.Set();
/*25*/   
/*26*/   }

as you can see : lines #21 , #24 are the replacement for the lock. 如你所见:第21行,第24行是锁的替代品。

Question : 题 :

  • Is it a valid replacement ? 它是有效的替代品吗? ( not that i will replace lock , but want to know about usages scenarios) (不是我会替换lock ,但想了解用法场景)
  • When should I use each ? 我什么时候应该使用?

Thank you. 谢谢。

strange but SO does not contain a question regarding _lock vs EventWaitHandle_ 奇怪,但SO不包含有关_lock vs EventWaitHandle_的问题

Do not go there. 不要去那儿。 An important property of a lock is that it provides fairness . 锁的一个重要特性是它提供了公平性 In other words, a reasonable guarantee that threads that contend for the lock get a guarantee that they can eventually acquire it. 换句话说,一个合理的保证,争夺锁的线程得到保证,他们最终可以获得它。 The Monitor class provides such a guarantee, implemented by a wait queue in the CLR. Monitor类提供了这样的保证,由CLR中的等待队列实现。 And Mutex and Semaphore provide such a guarantee, implemented by the operating system. 而Mutex和Semaphore提供了由操作系统实现的这种保证。

WaitHandles do not provide such a guarantee. WaitHandles 提供这样的保证。 Which is very detrimental if the lock is contended, the same thread can acquire it repeatedly and other threads can starve forever. 如果锁争用是非常有害的,同一个线程可以反复获取它,其他线程可以永远饿死。

Use an appropriate synchronization object for locks. 使用适当的锁定同步对象。 Wait handles should only be used for signaling. 等待句柄只应用于信令。

It is possible, but it is much slower than lock() and much harder to maintain. 这是可能的,但它比lock()慢得多,而且维护起来要困难得多。

By the way, you should never read a value directly when using Interlocked-methods to maintain it. 顺便说一句,在使用Interlocked-methods进行维护时,不应直接读取值。

Your code should look like this: 您的代码应如下所示:

var g = Interlocked.Increment(ref i);

Then g will contain the incremented value rather than an abitrary previous value. 然后g将包含递增的值而不是abitrary先前的值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM