是否有Waitone方法基本上调用重置?
-
29-09-2019 - |
题
我正在使用一个Autoresetevent,可以在事件(例外处理)上进行多个集呼叫。有时会调用额外的集合,因此,当代码在Waitone事件上进行第二个调用时,它就直接通过,因为门已经打开。
解决方案是在Waitone之前立即致电重置。是否有更干净的解决方案,或者这是唯一的方法?示例代码:
private void DoSomeWork()
{
Thread thrd = new Thread(new ThreadStart(DoSomeOtherStuff));
thrd.Start();
//mEvt.Reset();
mEvt.WaitOne();
//continue with other stuff
}
private void DoSomeOtherStuff()
{
/* lots of stuff */
mEvt.Set();
}
private void ExceptionTriggerNeedsToBreakOutOfDoSomeWork()
{
mEvt.Set();
}
处理例外之后,我需要再次致电Dosomework,但是由于SET可能被调用了多个例外(或Rethrown例外),因此Waitone只是流过。
我的解决方案是始终在Waitone之前致电重置。这是资助解决方案,设计差,还是有其他类型的事件可以处理这种情况?
编辑:我刚刚移动了事件旁边的评论重置(拟议的解决方案)。
解决方案
我担心的是,如果您在WaitOne()之前调用reset(),如果没有set()被调用,那么您会遇到麻烦。如果您调用Set(),则可能会发生这种情况,然后在击中Waitone()之前立即点击reset()。即使您两次调用set(),也不能保证您在两者之间都不会调用reset(),而不会释放任何机制。
理想情况下,您可以尝试.. catch..catch..finally block,并在最后块中调用set(),并且没有例外的处理。那对你有用吗?
汉斯是正确的,在这种情况下,多线程是不必要的。我的关注仅适用于您真正的多线程与WaitOne()的呼叫。
这也让我担心您正在调用不止一次的设置...这是否意味着当第一个套装被调用时,资源应该真正锁定?如果您仍然能够第二次点击Set(),对我来说,您仍在执行与共享资源一起使用的代码。在这种情况下,您不希望呼叫waitone()取消阻止。
另请注意,从MSDN:
不能保证对设定方法的每个调用都会释放线程。如果两个呼叫太近,以便在释放线程之前发生第二个呼叫,则仅释放一个线程。好像第二个电话没有发生。
无论如何,您的代码似乎应该去抛出异常的路线,或者跑步完成,但不能同时进行。即,您不应该两次调用Set()。
其他提示
这不是一个真正的问题,waitone()呼叫会自动重置事件。毕竟,您使用了Autoresetevent,而不是手动Resetevent。关键短语这里是自动重置。
看到它通过Waitone()呼叫向右蒸也很正常。您有一个不错的多重核心CPU,当您打电话给start()时,该线程立即开始启动,而仅需几微秒即可完成工作。毫秒,无论如何,比眼睛的眨眼更快。
也许更重要的是,您只是在这里不需要线程。开始一个,然后等待它完成是毫无意义的。只需直接调用剂量罩()即可。