我想创建一些线程,比如线程A,B,C,并阻止它们直到事件发生。当一个事件发生时,我想只发布一个线程。
例如:
Before event occurs:
Thread A : blocked
Thread B : blocked
Thread C : blocked
After event occurs:
Thread A : blocked
Thread B : unblocked
THread C : blocked
我读到AutoResetEvent
可以执行此操作,但我无法指定要解锁的线程,ManualResetEvent
将取消阻止所有被阻止的线程。
有没有办法实现我想做的事情?
答案 0 :(得分:5)
创建ManualResetEvent
的多个实例,每个Thread
一个实例,并在每个ManualResetEvent.WaitOne()
中使用Thread
,例如
public void StartThreadA()
{
_mreA = new ManualResetEvent();
_threadA = new Thread(new ThreadStart(() =>
{
_mreA.WaitOne();
// Continue
});
}
当你偶然发生时,你可以像这样处理它:
private void OnSomeEvent()
{
_mreA.Set();
}
这在规模方面非常有限,如果你打算使用大量的线程,我建议使用字典来查找每个线程的ManualResetEvent
。
<强>更新强>
我现在知道你正在使用一个线程队列,我会做类似以下的事情:
private Queue<ManualResetEvent> _queuedThreads = new Queue<ManualResetEvent>();
public void EnqueueThread()
{
var mre = new ManualResetEvent();
var thread = new Thread(new ThreadStart(() =>
{
mre.WaitOne();
// Continue
});
_queuedThreads.Enqueue(mre);
}
private void OnEvent()
{
var mre = _queuedThreads.Dequeue();
mre.Set();
}
答案 1 :(得分:0)
您应该考虑使用Semaphore而不是ManualResetEvent或AutoResetEvent。
文档here中有一个很好的基本示例。