I am curious whether it is possible to pause a thread t in Java and allow another thread to resume it later, by having t run the following pause code:
while(true) {
try {
synchronized(t) {
t.wait();
}
} catch(InterruptedException e) {
break;
}
}
And then resuming the thread t by calling .interrupt() on it. However, I have read about spurious wake-ups, and so I wondered whether my code can fail, in the sense of exiting the while-loop despite no other thread calling .interrupt() on it. While this answer and this answer state that there are no spurious interrupts, and hence my code will never fail, the Java docs does not seem to address this. My question probably boils down to whether InterruptedException is ever thrown without the thread being interrupted by .interrupt(). Is there any official source or documentation that confirms this?
Summary
So, although technically this works, there are numerous reasons why this should not be done. Oracle's documentation states that interruption should only be utilized for cancellations. But if you were to do this, it will clear the interrupt status and the previously waiting thread will receive an
InterruptedException.Alternative
Lets step through a brief, simplified example.
A
threadhere will obtain the monitor.The
threadwill begin to wait viawait(), and release the monitor. Always utilizewait()inside a conditional because threads are subject to get spurious wake-ups fromwait(). At this point, you have achieved forcing a thread to wait.Lets investigate how we go about returning the thread to work.
The
notify()will wake up the first waitingthreadon the monitor. Now, if you want all waiting threads to wake up, utilizenotifyAll()instead. This is the intended purpose and functionality ofwait()/notify()and thus should be utilized overwait()/interrupt(). For an additional example, see this article.