繁体   English   中英

多线程中的AutoResetEvent

[英]AutoResetEvent in Multi-threading

我下面有一个示例代码,该示例代码创建了多线程,并在单独的线程中的lock内包含了一块代码。 如果响应为null或autoReset.WaitOne(timeout)经过了时间跨度,那么我将中止子线程,以便允许队列中的下一个等待线程进入lock并执行操作。 但是这里的问题是,如果说ThreadA需要8秒钟来执行lock的复杂代码,那么下一个等待线程说ThreadB仅剩下2秒(因为所有线程同时启动AutoResetEvent's等待时间)。

我如何使每个线程具有相同的时间跨度来执行复杂的代码块。 我现在正尝试解决过去2天的问题,任何输入都会非常有帮助。

Class A
{
    static void Main(){
     for(int i=0; i < 2; i++)
      {
        var mainThread = new Thread(ParentThreadMethod);
        mainThread.Start();
      }
    }

    void ParentThreadMethod(){
      var autoReset = new AutoResetEvent(false);
      ClassB obj;
      var childThread = new Thread(() =>
        {
            obj = new ClassB();
            var result = obj.ChildThreadMethod();
            autoReset.Set();
        }       
         childThread.Start();

         // wait for 10sec
         autoReset.WaitOne(10000);           
    }
 } 

 Class B
 {
    private static readonly object threadLock = new object();
    string ChildThreadMethod(){
     lock (threadLock)
            {
                // complex logic taking 8sec 
            }
    }
 }

我认为问题在于两个线程共享对

private static readonly object threadLock = new object();

这意味着第二个线程将花费8秒等待第一个线程退出关键区域。 这使超时看起来快到了。 但是超时工作正常。

看来您只想在成功输入锁定后才开始超时。 这意味着线程本身必须启动超时,因为只有子线程知道何时进入锁。

它可能看起来像这样:

lock (threadLock) {
    var timeoutTask = Task.Delay(10000);
    var workTask = Task.Run(RunWork);
    var firstTask = Task.WhenAny(timeoutTask, workTask).Result;

    if (!workTask.IsCompleted) {
     AbortWork();
     workTask.Wait(); //Wait for cancellation to finish.
    }
}

通常,较新的TPL功能比线程和事件等更易于使用。如果此代码是新代码,我将从TPL类开始。

暂无
暂无

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

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