在记录异常时忽略ThreadAbortException的正确方法是什么?
仅仅在一个空的catch块中捕获它以使其消失是否安全?
发布于 2010-07-20 17:13:17
如果您需要停止在调用堆栈中进一步向上传播ThreadAbortException,可以调用Thread.ResetAbort。所以试着这样做:
try
{
// some code
}
catch (ThreadAbortException ex)
{
// do some logging
Thread.ResetAbort();
}至于“正确”--这取决于你的使用场景。我通常会对捕获它们保持谨慎,除非你确切地理解了它被抛出的原因。在stop中,它是一个“立即停止,迅速放下你正在做的事情”的信号。重置它并继续进行进一步处理时应谨慎操作。
发布于 2018-09-07 21:02:15
使用两个catch块:一个用于ThreadAbortException,另一个用于其余部分,例如:
void MainLoop()
{ bool workdone;
try
{ while( IsWorking ) // cross-thread volatile variable
{ workdone = Process();
if( !workdone )
{ Thread.Sleep( 500 ); }
}
}
catch( ThreadAbortException )
{ // Forced termination. Exit silently.
}
catch (Exception e)
{ LogError( e ); }
}发布于 2020-04-04 19:26:12
对于较新的.NET版本,忽略异常可以简化为
try
{ // ...
}
catch (Exception e) when (!(e is ThreadAbortException))
{ LogError( e );
}但这可能仍然不够。一些库倾向于用它们自己的异常包装所有的异常。在这种情况下,ThreadAbortExceptiononly可能会显示为InnerException。我不会称之为包装ThreadAbortException的最佳实践,但这是真实世界。
为了解决这个问题,我推荐一个扩展:
public static bool IsThreadAbort(this Exception ex)
{
while (ex != null)
{
if (ex is ThreadAbortException)
return true;
ex = ex.InnerException;
}
return false;
}现在,您可以使用以下命令进行检查:
catch (Exception e) when (!e.IsThreadAbort())
{ LogError( e );
}https://stackoverflow.com/questions/3281691
复制相似问题