wait()方法
方法wait()的作用是使当前执行代码的线程进行等待,wait() 方法是 Object 类的方法,该方法用来将当前线程置入 “预执行队列” 中,并且在 wait() 所在的代码行处停止执行,直到接到通知或被中断为止。
注意:
在调用 wait() 之前,线程必须获得该对象的对象级别锁,否则会抛出 illegalMonitorStateException 异常。在执行 wait() 方法后,当前线程释放锁。
notify()方法
方法notify() 也要在同步方法或同步块中调用,即在调用前,线程必须获得该对象的对象级别锁,否则会抛出 illegalMonitorStateException 异常。
该方法用来通知那些可能等待该对象的对象锁的其他线程,如果有多个线程等待,则由线程规划器随机挑选出齐总一个呈 wait 状态的线程,对其发出通知 notify。
注意:
1)执行 notify() 之后,当前线程不会马上释放该对象锁,呈 wait 状态的线程也并不能马上获取该对象锁,要等到执行 notify() 方法的线程将程序执行完,也就是退出 synchronized 代码块之后,当前线程才会释放锁,而呈 wait 状态的所在的线程才可以获取该对象锁。
2)当一个获得了对象锁的 wait 线程运行完毕,它会释放该对象锁,此时如果该对象没有再次使用 notify 语句,即便该对象已经闲置,其他 wait 状态等待的线程由于没有接到通知,还会继续阻塞在 wait 状态
示例
public class Test {
public static void main(String[] args) {
try {
Object lock = new Object();
MyThread1 t1 = new MyThread1(lock);
t1.start();
Thread.sleep(2000);
MyThread2 t2 = new MyThread2(lock);
t2.start();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
static class MyThread1 extends Thread {
private Object lock;
public MyThread1(Object lock) {
this.lock = lock;
}
@Override
public void run() {
try {
synchronized (lock) {
System.out.println("开始 wait");
lock.wait();
System.out.println("结束 wait");
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
static class MyThread2 extends Thread {
private Object lock;
public MyThread2(Object lock) {
this.lock = lock;
}
@Override
public void run() {
synchronized (lock) {
System.out.println("开始 notify");
lock.notify();
System.out.println("结束 notify");
}
}
}
}
运行结果: