📅  最后修改于: 2023-12-03 15:16:30.643000             🧑  作者: Mango
在Java中,多线程的处理是一个很常见的问题。而在多个线程之间需要进行交互的时候,就需要使用wait()方法和notify()/notifyAll()方法来实现线程的协调和同步。
wait()方法是一个对象中的方法,它的作用是让线程等待。当一个线程执行到该方法时,它会进入到该对象的等待池中,同时释放该对象的锁。线程在等待期间,不会占用CPU资源。只有当其他线程调用该对象的notify()/notifyAll()方法时,等待的线程才会被唤醒,重新进入到该对象的锁池中,等待获取锁。
wait()方法有三个重载的版本,其基本使用方式如下:
public synchronized void wait() throws InterruptedException;
public synchronized void wait(long timeout) throws InterruptedException;
public synchronized void wait(long timeout, int nanos) throws InterruptedException;
其中,第一个版本是无限等待,直到其他线程调用该对象的notify()/notifyAll()方法;第二个版本是等待一定的时间(timeout)后再重新尝试获取锁,如果这段时间内没有其他线程调用该对象的notify()/notifyAll()方法,那么线程就会自动唤醒;第三个版本是等待指定的时间(timeout+nanos)后再尝试获取锁。
下面用一个简单的示例来说明wait()方法的使用:
public class WaitExample{
public static void main(String[] args){
final Object lock = new Object(); // 定义一个锁对象
Runnable runnable1 = new Runnable(){
@Override
public void run(){
synchronized(lock){ // 获取锁
try{
System.out.println("线程1开始等待...");
lock.wait(); // 线程1等待
}catch(InterruptedException e){
e.printStackTrace();
}
System.out.println("线程1被唤醒了。");
}
}
};
Runnable runnable2 = new Runnable(){
@Override
public void run(){
synchronized(lock){ // 获取锁
System.out.println("线程2开始唤醒线程1...");
lock.notify(); // 唤醒线程1
}
}
};
new Thread(runnable1).start(); // 启动线程1
new Thread(runnable2).start(); // 启动线程2
}
}
上述代码中,通过synchronized关键字来获取同一对象的锁,然后在线程1中调用lock.wait()方法使线程1进入等待状态。而在线程2中,如果不调用lock.notify()方法,线程1将一直处于等待状态。输出结果如下:
线程1开始等待...
线程2开始唤醒线程1...
线程1被唤醒了。
从输出结果可以看出,线程1在调用wait()方法后进入了等待状态,而线程2调用了notify()方法后唤醒了线程1,让其重新进入到锁池中等待获取锁。