ThreadAbortException有哪些不良后果?

3

我最近在一份遗留代码中发现了一个多线程模式,该模式依赖于Thread.Abort()方法来取消对外部系统的同时请求。其中一个不良后果是很难区分超时异常和其他异常类型。

除此之外,还有哪些原因不能在多线程控制流中使用ThreadAbortException呢?


调用 Thread.Abort 就像是在想让司机停车时朝他的头部开枪。无论哪种方式,汽车都会停下来,但前者的后果是不可预测的,可能会对其他人以及司机本人造成灾难性的影响。 - Jim Mischel
1个回答

5
有哪些其他原因不使用ThreadAbortExceptions来处理多线程控制流?
Thread.Abort可能会使线程处于非常奇怪的状态,这可能无法干净地处理。
Thread.Abort的文档中可以看到:
如果一个线程调用另一个线程的Abort方法,则该中断将打断正在运行的任何代码。还有一种可能是静态构造函数被中止。在极少数情况下,这可能会阻止在该应用程序域中创建该类的实例。在.NET Framework版本1.0和1.1中,有可能线程在finally块运行时中止,此时finally块被中止。
如果您正在编写多线程代码,则这可能更加危险,因为它可能会触发死锁。这也有记录:
调用Abort的线程可能会阻塞,如果被中止的线程处于受保护的代码区域(例如catch块、finally块或受限执行区域)中。如果调用Abort的线程持有被中止线程需要的锁,则可能会发生死锁。
一般来说,使用框架的合作式取消模型比调用Thread.Abort更安全、更干净。使用CancellationTokenCancellationTokenSource可以让您以清晰的方式设计适当的取消,并且线程可以正确地处理自己的清理工作。

即使您不在多线程代码中工作,它在catch/finally期间(或之前!)中止的事实也是危险的。 即使您不担心死锁,这意味着它可能不会放弃应该放弃的资源-留下文件被写锁定,未删除的临时文件,连接到服务器打开等。 - neminem

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接