obj.wait()让进入object监视器的线程到WaitSet等待/让持有obj的锁的线程到WaitSet中等待;
obj.notify()在object上正在WaitSet等待的线程中挑一个唤醒,是随机唤醒;
obj.notifyAll()让object上正在WaitSet等待的线程全部唤醒;
它们都是线程之间协作的手段,都属于Object类的方法。必须获得此对象的锁,才能调用这几个方法。所以wait和notify必须进入synchronized块中才可以使用,即必须拿到对象的锁才可以使用上述方法。
public class TestWaitNotify {
final static Object obj = new Object();
public static void main(String[] args) throws InterruptedException {
new Thread(()->{
synchronized (obj){
System.out.println("执行...");
try {
obj.wait();//让线程1在obj上等待下去
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("其它代码...");
}
},"t1").start();
new Thread(()->{
synchronized (obj){
System.out.println("执行...");
try {
obj.wait();//让线程2在obj上等待下去
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("其它代码...");
}
},"t2").start();
//主线程两秒后执行
Thread.sleep(2);
System.out.println("唤醒obj上其它线程");
synchronized (obj){
obj.notify();
}zheng
}
}
wait方法详解:
1、wait()
如果wait方法无参数,代表该线程会一直等待下去,直到被notify方法或者notifyAll方法唤醒才可以进入EntryList中。线程本身不会自动苏醒。源码中实际是调用了wait(0)实现一直等待。
2、wait(timeout)
单个参数的wait(timeout)方法表示线程等待毫秒级时间,如果没有notify唤醒该线程,那么时间结束后线程会自动苏醒进入EntryList队列,如果线程在timeout结束前就被notify方法唤醒,那么则不会继续等待,提前进入EntryList队列中。
wait vs sleep:
注意wait方法和sleep方法的区别,sleep方法是线程想睡就睡,如果线程持有锁调用sleep方法后并不会释放锁。wait方法是只有当线程持有锁后才可以调用wait方法,而且调用wait方法后会释放锁。