为什么我的代码停止而没有返回异常?

时间:2010-05-11 14:01:34

标签: c# multithreading exception

我有一些代码启动了几个线程让它们执行,然后使用while循环来检查当前时间是否超过设置的超时时间,或者是否已经处理了正确的结果数量(通过检查类对象上的int)(在循环之间等待Thread.Sleep()

一旦while循环设置为exit,它就会在线程上调用Abort(),并且应该将数据返回给调用该方法的函数。

在调试和单步执行代码时,我发现在单独的线程上运行的代码中可能存在异常,在某些情况下我会适当地处理这些异常,而在其他时候我不想做任何具体的事情。

我所看到的是我的代码进入while循环并且线程休眠,然后我的函数(数据或异常)都没有返回任何内容。代码执行完全停止。

任何想法可能会发生什么?


代码示例:

System.Threading.Thread sendThread = 
     new System.Threading.Thread(new System.Threading.ThreadStart(Send));
sendThread.Start();

System.Threading.Thread receiveThread = 
     new System.Threading.Thread(new System.Threading.ThreadStart(Receive));
receiveThread.Start();

// timeout
Int32 maxSecondsToProcess = this.searchTotalCount * timeout;
DateTime timeoutTime = DateTime.Now.AddSeconds(maxSecondsToProcess);
Log("Submit() Timeout time: " + timeoutTime.ToString("yyyyMMdd HHmmss"));

// while we're still waiting to receive results & haven't hit the timeout, 
// keep the threads going
while (resultInfos.Count < this.searchTotalCount && DateTime.Now < timeoutTime)
{
    Log("Submit() Waiting...");
    System.Threading.Thread.Sleep(10 * 1000); // 1 minute
}

Log("Submit() Aborting threads");    // <== this log doesn't show up

sendThread.Abort();
receiveThread.Abort();

return new List<ResultInfo>(this.resultInfos.Values);

2 个答案:

答案 0 :(得分:5)

所以,你真的不应该在线程上使用Sleep方法进行同步。这就是ManualResetEvent等同步类的用途,以及异步编程模型(IAsyncResult实现)。

这里更好的方法是创建一个委托,其中包含要异步运行的方法的签名。然后,将作为异步操作入口点的方法组分配给该委托的实例,并在委托实例上调用BeginInvoke。

从那里开始,你会运行你的循环,期望你在调用BeginInvoke返回的IAsyncResult实现的WaitOne属性返回的WaitHandle上调用AsyncWaitHandle的重载代表。

这将减少对Sleep方法的依赖(通常不利于同步)。

如果您可以选择使用.NET 4.0,那么您可能需要查看Task class中的System.Threading.Tasks namespace,因为它提供了一种更好的方法来处理异步处理,取消,并等待超时。

答案 1 :(得分:3)

Thread.Abort在调用它的线程中引发ThreadAbortException

你不应该让异常从你的线程中逃脱 - 你应该在你的线程对象中进行异常处理。至少应该在线程对象的代码周围有一个try \ catch块。