以下代码

时间:2019-08-12 16:21:16

标签: java multithreading sleep interrupt

第二个循环实际上如何中断正在休眠的主线程,而第一个则不? 我的理解是在Thread.sleep(3000)之后,代码Thread.currentThread()。interrupt()将在3秒后执行。 谁能解释它的实际工作原理

for (int i = 0; i < 2; i++) {
            try {
                System.out.println("loop : " + i);
                Thread.sleep(3000);
                System.out.println("Woke up");
                Thread.currentThread().interrupt();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
loop : 0
Woke up
loop : 1
java.lang.InterruptedException: sleep interrupted
exception loop:1
    at java.base/java.lang.Thread.sleep(Native Method)
    at multithreadings.Mainclass.main(Mainclass.java:13)

4 个答案:

答案 0 :(得分:4)

中断是有礼貌的停止请求:线程没有义务停止。

这就像罗宾·威廉姆斯(Robin Williams)关于what police in the UK say when you commit a crime的笑话一样:

  

停止!否则我会再说一遍!

此外,中断线程并不会引发to:它只是在线程上设置一个标志。如果某物(例如InterruptedException)检查了此标志并发现它已设置,则可能会抛出Thread.sleep;但是标志和异常是指示中断的两种正交方式。

因此:

  • 第一次执行时,您睡眠3秒钟,然后设置中断标志,循环主体正常完成。
  • 在第二次执行时,您要求睡眠3秒,但是InterruptedException检测到中断的标志并引发异常。

答案 1 :(得分:1)

您发布的代码中涉及一个线程。该线程执行循环。在第一次迭代时,线程会自行中断。中断并不意味着“立即停止执行”。意思是:“请允许我停止跑步。”

想要尊重中断请求的线程可以通过两种方式做到这一点:

  1. 它会定期检查是否已被中断,如果是这种情况,则会停止执行(例如,通过中断循环或返回)
  2. 它调用诸如sleep()之类的阻塞方法,如果线程已被中断或正在被中断,则该方法将引发InterruptedException。

发生第二种情况。在调用sleep()之后,在第一次迭代中完成了中断请求。线程继续运行,并在第二次迭代时调用sleep(),因为该线程之前已被中断,所以会引发InterruptedException。

答案 2 :(得分:1)

在Java中,一个线程无法停止另一个线程。一个线程只能请求另一个线程停止。该请求以中断的形式发出。在线程实例上调用 interrupt()方法会将实例上的中断状态设置为 true

一旦中断状态设置为为真,所有阻塞方法都会通过引发InterruptedException来响应中断。,如果要详细检查,请阅读以下文章。了解Thread Interruption在Java中的工作原理。

答案 3 :(得分:0)

阅读文档,即interrupt()的Javadoc:

  

中断该线程。

     

除非当前线程正在中断自身,这总是允许的,...

     

如果该线程被阻止...

     

如果该线程被阻止...

     

如果该线程被阻止...

     

如果以上条件均不满足,则将设置此线程的中断状态

sleep(long millis)

  

如果任何线程中断了当前线程,则抛出InterruptedException。抛出此异常时,将清除当前线程的中断状态。

由于线程已在循环的第二次迭代中自行中断,从而设置了自己的中断状态,因此sleep(...)方法立即被中断。