volatile boolean hasFuTou = false;
volatile boolean hasLangTou = false;
@Test
public void testWait() throws InterruptedException {
ReentrantLock workRoom = new ReentrantLock();
Condition sleepRoom = workRoom.newCondition();
Condition smokeRoom = workRoom.newCondition();
Thread laoli = new Thread(() -> {
workRoom.lock();
try {
log.info("老李进入工作区");
//使用while循环防止虚假唤醒
while (!hasFuTou) {
log.info("没有斧头,没干成活,进入休息室,让出工作区");
try {
sleepRoom.await();
} catch (InterruptedException e) {
log.info("休息被打断");
}
}
log.info("老李开始干活");
} finally {
workRoom.unlock();
}
});
laoli.setName("老李");
laoli.start();
Thread laowang = new Thread(() -> {
workRoom.lock();
try {
log.info("老王进入工作区");
//使用while循环防止虚假唤醒
while (!hasLangTou) {
log.info("没有榔头,没干成活,进入吸烟室,让出工作区");
try {
smokeRoom.await();
} catch (InterruptedException e) {
log.info("休息被打断");
}
}
log.info("老王开始干活");
} finally {
workRoom.unlock();
}
});
laowang.setName("老王");
laowang.start();
Thread.sleep(1000);
workRoom.lock();
try {
log.info("老板进入工作区,送来斧头和榔头,通知干活");
hasFuTou = true;
//有斧头了,唤醒老李
sleepRoom.signal();
hasLangTou = true;
//有榔头了,唤醒老王
smokeRoom.signal();
}finally {
workRoom.unlock();
}
}
输出如下
11:34:54.025 [老李] INFO com.wkt.juc.ReentrantLockTest - 老李进入工作区
11:34:54.031 [老李] INFO com.wkt.juc.ReentrantLockTest - 没有斧头,没干成活,进入休息室,让出工作区
11:34:54.031 [老王] INFO com.wkt.juc.ReentrantLockTest - 老王进入工作区
11:34:54.031 [老王] INFO com.wkt.juc.ReentrantLockTest - 没有榔头,没干成活,进入吸烟室,让出工作区
11:34:55.025 [main] INFO com.wkt.juc.ReentrantLockTest - 老板进入工作区,送来斧头和榔头,通知干活
11:34:55.025 [老李] INFO com.wkt.juc.ReentrantLockTest - 老李开始干活
11:34:55.025 [老王] INFO com.wkt.juc.ReentrantLockTest - 老王开始干活