Skip to content

Instantly share code, notes, and snippets.

@jeremyheiler
Last active August 29, 2015 14:04
Show Gist options
  • Save jeremyheiler/1a5e8961bb132f9cd4f8 to your computer and use it in GitHub Desktop.
Save jeremyheiler/1a5e8961bb132f9cd4f8 to your computer and use it in GitHub Desktop.
Basic example of using wait() and notify().
public class Main {
public static final Object LOCK = new Object();
public static void main(String[] args) throws InterruptedException {
new Thread(new A()).start();
new Thread(new B()).start();
}
}
class A implements Runnable {
@Override
public void run() {
try {
long n = System.currentTimeMillis();
synchronized (Main.LOCK) {
System.out.println("waiting...");
Main.LOCK.wait(2000); // change this to wait less, more, or indefinitely
}
System.out.println("waited for " + (System.currentTimeMillis() - n) + "ms");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
class B implements Runnable {
@Override
public void run(){
try {
System.out.println(0);
for (int i = 1; i <= 5; ++i) {
Thread.sleep(1000);
System.out.println(i);
}
synchronized (Main.LOCK) {
Main.LOCK.notify();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
@jeremyheiler
Copy link
Author

Basic Wait and Notify Program

What does this program do?

The program starts up two threads, which I'll denote by the class of Runnable given to them: A and B. Each thread is started as soon as they're created. The Main class provides a global lock that both threads will synchronize on.

Thread A grabs the monitor for the lock and calls wait() on it, blocking the thread until another thread obtains the monitor for the lock and notifies it. (This is unclear to me. Calling wait() must temporarily release the monitor for the lock in order for another thread to obtain it.) Once wait() returns, the milliseconds it waited for is printed to standard out.

Thread B does some work to pass time. In this case a loop iterates five times, sleeping for a second and printing the current count on each iteration. The count is printed so that it can be compared to how long thread A waits. Once this work is done, the monitor for the lock is obtained and the lock is notified. This will ultimately unblock thread A.

Waiting with a timeout

If thread A calls wait() with a timeout less than five seconds, it will unblock itself before thread B is given the opportunity to notify it. If the timeout is greater than five seconds, then thread B will end up notifying thread A and unblocking it before the timeout occurs.

Questions

  • How does thread B obtain the lock to notify thread A? (Nothing, except the first two printed lines are in a different order. That makes sense, though.)
  • Does the lock need to be the same as the one used for wait and notify?
  • Does LOCK need to be volatile? (I think it doesn't. It's final and never updated.)
  • Does this program change if thread B is started first?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment