This is the sixth day of my participation in the August More text Challenge. For details, see: August More Text Challenge
Initial wait(), notify(), and notifyAll()
The methods wait(), notify(), and notifyAll(), although they operate on threads, are not specific to threads. They are Object methods. So what’s so magical about these three methods that can block a thread and wake it up? Let’s start with the wait() method.
Here are three overloaded methods for wait()
public final void wait() throws InterruptedException
public final void wait(long timeout) throws InterruptedException
public final void wait(long timeout , int nanos) throws InterruptedException
- All three overloads of the wait() method will call the wait(Long Timeout) method. The wait() method mentioned above is equivalent to wait(0), which means it never times out.
- The Object’s wait(Long Timeout) method causes the current thread to block until another thread calls the Object’s notify() or notifyAll() method, or until the timeout time is reached.
- The wait() method must own the object’s monitor (resource/lock), which means the wait() method must be used in Synchronized methods.
- After the current thread executes the wait() method on the object, it relinquishes its ownership of the monitor and enters the wait set associated with the object. There is also an opportunity for other threads to continue competing for ownership of the Monitor.
About the notify ()
private final native void notify();
- Wakes up a single thread executing the object’s wait() method
- If a thread is blocked due to the object’s wait() method, it is awakened, if not, it is ignored.
- The awakened thread needs to reacquire the lock of the monitor associated with the object before execution can continue.
Notice for notify() and wait()
- The wait() method is interruptible, which means that once the current thread is blocked by calling wait(), another thread can interrupt it by using the interrupt method. When an interruptible method is interrupted, it receives InterruptedException and the interrupt flag is erased.
- After a thread executes the wait() method on an object, it is added to the corresponding wait set, and each object’s monitor has a wait set associated with it.
- When a thread enters a wait set, the notify method can wake it up, that is, it is ejected from the wait set, and interrupt the wait thread to wake it up.
- The wait() and notify() methods must be used in synchronized methods because the prerequisite for wait() and notify is that ownership of the synchronized method’s monitor must be held.
- The monitor of synchronized code must be consistent with the object that executes wait() and notify() methods. Simply put, the object whose monitor must be synchronized can only be used for wait() and notify() operations
The instance
- New An Object as a monitor
- The Wait class implements the run method to output the acquired lock in the synchronized block and executes the Wait () method to release the Object (monitor).
- The Notify class gets the lock, the output grabs the resource, and wakes up the blocked thread to continue executing the current thread until it finishes (important)
- The Wait class wakes up and continues with subsequent output
private static Object object = new Object();
static class Wait implements Runnable{
@Override
public void run(a) {
synchronized (object){
System.out.println("Current thread"+ Thread.currentThread().getName()+"Got the lock.");
/ / release
try {
object.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("Got the lock back, thread name."+Thread.currentThread().getName()); }}}static class Notify implements Runnable{
@Override
public void run(a) {
synchronized (object){
System.out.println("Someone released the lock. I grabbed the resource."+Thread.currentThread().getName());
/ / wake
object.notify();
System.out.println("It's over."); }}}public static void main(String[] args) {
Thread thread1 = new Thread(new Wait());
Thread thread2 = new Thread(new Notify());
thread1.start();
try {
Thread.sleep(300);
} catch (InterruptedException e) {
e.printStackTrace();
}
thread2.start();
}
Copy the code
The results of
The current Thread thread-0 acquired the lock. Someone released the lock. I grabbed the resource thread-1
Wait and sleep.
On the surface, both wait and sleep methods can put the current thread into a blocked state, but there are essential differences between the two.
- Both wait and sleep can cause a thread to block
- Both wait and sleep methods are interruptible methods, and both methods receive interrupt exceptions after they are interrupted.
- Wait is the Object method, and sleep is specific to Thred
- Execution of the WAIT method must be synchronized; sleep does not
- When a thread executes the sleep method, monitor (lock) is not released, but wait (lock) is
- The sleep method actively exits the block after a set time to sleep, while the wait method (which does not specify a time, defaults to 0 and blocks permanently) needs to be interrupted by another thread before exiting the block.