A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 冯国强 中级黑马   /  2013-11-16 16:57  /  1286 人查看  /  2 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

多线程间的通信,毕老师讲授的生产者与消费者两个线程,唤醒所有线程notifyAll方法唤醒进程,本质是什么?为什么使用notifyAll方法唤醒会解决多个线程生产,多个线程消费之间的安全问题呢?为什么老师说唤醒所有线程要重新判断是否有物品?

评分

参与人数 1技术分 +1 收起 理由
FFF + 1 淡定

查看全部评分

2 个回复

倒序浏览
notifyAll是唤醒在此对象监视器上等待的所有线程。线程通过调用其中一个 wait 方法,在对象的监视器上等待。
直到当前线程放弃此对象上的锁定,才能继续执行被唤醒的线程。被唤醒的线程将以常规方式与在该对象上主动同步的其他所有线程进行竞争;例如,唤醒的线程在作为锁定此对象的下一个线程方面没有可靠的特权或劣势。 这个就是Object中的一个唤醒方法,而且notifyAll必须前提是在监视器上,所以在Synchronized这个监视器里面才会运行。
如果有多个线程,只用notify唤醒的话会导致多个线程全部等待在哪,全都放弃执行资格。原因你可以重新听一遍视频里毕老师加完while后再加notifyAll那一段(细说确实很麻烦)。就是说只要一个线程进去之后执行完就唤醒所有在这个监视器上等待的线程,避免线程发生类似于死锁的情况,无法继续运行。

评分

参与人数 1技术分 +1 收起 理由
FFF + 1

查看全部评分

回复 使用道具 举报
唤醒所有线程notifyAll方法唤醒进程,本质是什么?
答:本质就是所有线程都启动,谁抢到cpu谁就执行。

为什么使用notifyAll方法唤醒会解决多个线程生产,多个线程消费之间的安全问题呢?
因为如果你使用notify方法只唤醒所有线程中的一个线程,这个线程可能是生产者的。而生产者有个判断就是如果生产了但是没消费掉的话,生产者就陷入冻结,这样就是我刚把生产者另一个线程唤醒然后我沉睡,另外那个线程醒了后一看库房里的东西还没被消费掉,那么接着陷入冻结。就有可能生产者和消费者都冻结了,那程序就停了不继续运行了。使用notifyAll就是把生产者和消费者都唤醒,然后它们抢cpu谁抢到谁执行,这样就不会所有线程都冻结了。多个线程之间因为有同步,所以不会有安全问题。

为什么老师说唤醒所有线程要重新判断是否有物品?
因为刚睡醒大家都不知道到底库房里有没有东西,所以需要使用while语句让线程醒来第一件事就是判断库房里到底有没有东西。
如果有东西说明生产者其中的某个线程刚生产过,那么我冻结等消费者线程抢到cpu后消费掉库房里的东西;如果没东西说明消费者刚消费过,那么生产者当中谁活着谁就生产。

评分

参与人数 1技术分 +1 收起 理由
FFF + 1

查看全部评分

回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马