educative.io

We are calling interrupt twice?

In the below code snippet, we are calling interrupt twice, after first interrupt, exception is thrown but why the status of thread.isInterrupted is false? Do we always need to call another interrupt to set the status?

public void run() {
                try {
                    System.out.println("I am too sleepy... Let me sleep for an hour.");
                    Thread.sleep(1000 * 60 * 60);
                } catch (InterruptedException ie) {
                    System.out.println("The interrupt flag is cleard : " + Thread.interrupted() + " " + Thread.currentThread().isInterrupted());                  
                    Thread.currentThread().interrupt();
                    System.out.println("Oh someone woke me up ! ");
                    System.out.println("The interrupt flag is set now : " + Thread.currentThread().isInterrupted() + " " + Thread.interrupted());                                    
                  
                }
            }
        });

        sleepyThread.start();

        System.out.println("About to wake up the sleepy thread ...");
        sleepyThread.interrupt();
        System.out.println("Woke up sleepy thread ...");

        sleepyThread.join();

Course: Java Multithreading for Senior Engineering Interviews - Learn Interactively
Lesson: Interrupting Threads - Java Multithreading for Senior Engineering Interviews

Hi @Beda_Rath !!
In the given code snippet, the status of Thread.currentThread().isInterrupted() is false after the first call to Thread.interrupted(), even though an InterruptedException is thrown. This behavior occurs because the Thread.interrupted() method not only returns the interrupted status of the thread but also clears the interrupted status.

Let’s break down the code to understand the sequence of events:

  1. The sleepyThread is started and enters the run() method.
  2. Inside the run() method, the thread goes to sleep for one hour using Thread.sleep(1000 * 60 * 60).
  3. While the thread is sleeping, the sleepyThread.interrupt() is called from the main thread.
  4. The interrupted status of the sleepyThread is set, and an InterruptedException is thrown.
  5. Inside the catch block, the first call to Thread.interrupted() is made. This method not only returns the interrupted status but also clears the interrupted status of the current thread. Since the interrupted status was set, Thread.interrupted() returns true and clears the interrupted status.
  6. The Thread.currentThread().interrupt() is called to set the interrupted status again.
  7. After setting the interrupted status again, the second call to Thread.interrupted() is made. However, since the interrupted status was already cleared by the first call to Thread.interrupted(), it returns false.

So, calling Thread.interrupted() once clears the interrupted status, and calling it again returns false because the status was already cleared. The subsequent call to Thread.currentThread().isInterrupted() would correctly reflect the interrupted status, which should be true in this case.

In summary, you don’t need to call another interrupt() to set the interrupted status. It is set initially when the thread is interrupted, and you can check its status using Thread.currentThread().isInterrupted() without calling Thread.interrupted() again.
We used two methods to check for the interrupt status of a thread. One is the static method Thread.interrupted() and the other is Thread.currentThread().isInterrupted() . The important difference between the two is that the static method would return the interrupt status and also clear it at the same time. On line 22 we deliberately call the object method first followed by the static method. If we reverse the ordering of the two method calls on line 22, the output for the line would be true and false , instead of true and true .
I hope it helps.Happy Learning :blush: