为什么Thread.stop不能在Thread.interrupt不起作用的情况下工作?

时间:2011-03-09 10:19:23

标签: java multithreading

Thread.stop()上的官方 Sun Oracle立场是不应该使用它。在其他论点中,they write

  

应该注意的是,在等待线程没有响应Thread.interrupt的所有情况下,它也不会响应Thread.stop。

但我不明白。如果一个线程正在忙于处理某些事情(不仅仅是等待或阻塞外部资源)并且没有明确检查中断标志,那么Thread.interrupt()Thread.stop()仍然有效时不会ThreadDeath做任何事情抛出{{1}})?

4 个答案:

答案 0 :(得分:4)

  

但我不明白。如果一个线程正在忙于处理某些事情(不只是在外部资源上等待或阻塞)并且没有明确地检查中断标志,那么当Thread.stop()仍然有效时,Thread.interrupt()不会做任何事情(抛出ThreadDeath)?

我认为你误解了引用的文字。它指的是正在等待的线程,而不是正在运行的线程。具体而言,它指的是如下情况:

  • 当线程在I / O调用中被阻止时,低级JVM实现问题会阻止它响应stopinterrupt

  • 一个不想被停止的线程可以捕获ThreadDeath,这类似于一个不想被中断而只是忽略该标志的线程。

答案 1 :(得分:2)

Thread.stop不是关于能够挽救线程的好或坏编码的问题。 除非作为最后的手段,否则不应该使用它。可以执行你的代码并期望发生Thread.stop(),但在这种情况下,interrupt()可以做得很好。

stop()在interrupt()没有的情况下不起作用的问题(即在某些原生内容上被阻塞):stop和ineterrupt都会使用相同的本机信号来进行调用。

在POSIX上,如果SIGUSR2(例如)没有帮助本机代码挽救,它将无助于中断/停止。 您可以将中断与停止视为:两者都可以使用OS信号。本机代码可能不支持OS信号。但是,如果它们是:stop()也将Throwable放在将在java代码中传播的堆栈上。相反,中断只设置一个标志。

然而,throwable可能会在任何语句中弹出,因此某些不变量可能无法正确处理。

可能通过抛弃大型状态,回滚交易等等,可以通过Thread.uncaughtExceptionHandler进行部分修复......再次:不可取。

答案 2 :(得分:0)

据我了解,主要原因是ThreadDeath异常可能被抛出,而中间标志必须明确检查。

考虑在线程中运行的代码:

public void sellItem(Store s) {
   synchronized (s) {
       if (s.itemsAvailable > 0) {
           s.itemsAvailable--;
           s.itemsSold++;
       }
   }
}

如果在s.itemsAvailable--之后抛出ThreadDeath,则Store对象将处于不一致状态。另一方面,这段代码是安全的:

public void sellLoop(Store s) {
    while (!Thread.interrupted())
       sellItem(s);
}

来源:http://download.oracle.com/javase/1.5.0/docs/api/java/lang/Thread.html#stop%28%29

他们说Thread.stop()不起作用,因为(我猜)可以捕获并忽略throwable。

答案 3 :(得分:-1)

如果JVM太忙而无法中断线程,那么它也太忙而无法杀死它。