多线程间的通信 wait()、notify()、notifyAll()
来源:互联网 发布:斑马gk888t编辑软件 编辑:程序博客网 时间:2024/06/07 07:25
多线程如何进行线程间的通信
测试代码:
// class Servicepublic class Service { public void testMethod(Object lock) { try{ synchronized (lock) { System.out.println("begin wait() ThreadName=" + Thread.currentThread().getName()); lock.wait(); System.out.println("end wait() ThreadName=" + Thread.currentThread().getName()); } } catch(InterruptedException e) { e.printStackTrace(); } }}// class ThreadApublic class ThreadA extends Thread{ private Object lock; public ThreadA(Object lock) { this.lock = lock; } @Override public void run() { Service s = new Service(); s.testMethod(lock); }}// class ThreadBpublic class ThreadB extends Thread{ private Object lock; public ThreadB(Object lock) { this.lock = lock; } @Override public void run() { Service s = new Service(); s.testMethod(lock); }}// class ThreadCpublic class ThreadC extends Thread{ private Object lock; public ThreadC(Object lock) { this.lock = lock; } @Override public void run() { Service s = new Service(); s.testMethod(lock); }}// class NotifyThreadpublic class NotifyThread extends Thread{ private Object lock; public NotifyThread(Object lock) { this.lock = lock; } @Override public void run() { synchronized (lock) { lock.notify();// lock.notify();// lock.notify();// lock.notify();// lock.notifyAll(); } }}// class Mainpublic class Main { public static void main(String[] args) { service(); } private static void service() { try{ Object lock = new Object(); ThreadA ta = new ThreadA(lock); ta.start(); ThreadB tb = new ThreadB(lock); tb.start(); ThreadC tc = new ThreadC(lock); tc.start(); Thread.sleep(3000); // 主线程睡眠3秒钟 NotifyThread notifyThread = new NotifyThread(lock); notifyThread.start(); } catch(InterruptedException e) { e.printStackTrace(); } }}
输出结果(程序还在执行状态,并没有退出,因为还有两个线程处于等待状态):
begin wait() ThreadName=Thread-0begin wait() ThreadName=Thread-1begin wait() ThreadName=Thread-2end wait() ThreadName=Thread-0
从以上输出中我们可以得知Thread-0首先获得了lock对象的对象锁,然后执行到lock.wait()后,Thread-0线程进入等待状态并释放了lock对象的对象锁、然后是Thread-1、Thread-2线程依次执行Thread-0的步骤。最后三个线程均进入等待状态并将lock对象的对象锁释放掉。主线程在等待了三秒后创建了notifyThread对象并新创建了一个线程,notifyThread线程获取lock对象的对象锁后执行lock.notify()方法随机唤醒三个等待线程中的一个(从打印结果看出随机唤醒的是Thread-0),被唤醒的线程继续执行lock.wait()后续代码,直至该线程的任务执行完毕。
结论:notify一次只能随机唤醒一个在等待的线程,如果存在多个等待线程,其他没被唤醒的线程会继续等待下去。
将NotifyThread的run方法内的lock.notify()全部解开注释,如下:
@Overridepublic void run() { synchronized (lock) { lock.notify(); lock.notify(); lock.notify(); lock.notify();// lock.notifyAll(); }}
执行后的输出结果:
begin wait() ThreadName=Thread-0begin wait() ThreadName=Thread-1begin wait() ThreadName=Thread-2end wait() ThreadName=Thread-0end wait() ThreadName=Thread-2end wait() ThreadName=Thread-1
从以上输出结果可以看出,虽然执行了四次lock.notify()方法,但是只有三个线程处于等待状态,多次执行lock.notify()会被系统自动忽略。每次执行完lock.notify()方法后都会随机唤醒一个处于等待状态的线程。
我们将NotifyThread的run方法内的lock.notify();方法全部注释掉,解开lock.notifyAll();的注释代码,如下所示:
@Overridepublic void run() { synchronized (lock) {// lock.notify();// lock.notify();// lock.notify();// lock.notify(); lock.notifyAll(); }}
再次执行后输出如下:
begin wait() ThreadName=Thread-0begin wait() ThreadName=Thread-2begin wait() ThreadName=Thread-1end wait() ThreadName=Thread-1end wait() ThreadName=Thread-2end wait() ThreadName=Thread-0
从以上结果可以看出,lock.notifyAll()方法会将所有处于等待的线程全部唤醒,也就不需要去关心有多少线程处于等待状态了。
通过wait()和notify(),notifyAll()方法可以实现线程件的通信。
- 多线程间的通信 wait()、notify()、notifyAll()
- 多线程通信( wait(),notify(),notifyAll() )
- java的线程通信wait(),notify(),notifyAll()
- wait/notify/notifyAll实现线程间通信
- 多线程的notify,notifyAll,wait实践
- JAVA多线程的理解wait、notify、notifyAll
- java多线程wait() ,notify() notifyAll()
- 【多线程_basic】 wait/notify/notifyAll
- 多线程wait-notify;notifyall.sleep
- 多线程中wait(),notify(),notifyAll()
- 【Java多线程与并发库】04 传统的线程同步通信技术-synchronized/wait/notify/notifyAll
- 多线程五,线程间通信,wait、notify,notifyAll方法(14,毕向东老师)
- 多线程五,线程间通信2,wait、notify,notifyAll方法(14,毕向东老师)
- java多线程-线程间通信-示例代码-解决安全问题-等待唤醒机制wait()notify()notifyAll()
- jvm的线程之间的通信-notify-wait-notifyAll
- 线程之间的同步和通信,synchronized,wait(),notify(),notifyAll()
- Java多线程设计wait、notify、notifyall、synchronized的使用机制
- java多线程当中wait notify notifyAll的使用
- Linux IO模式及 select、poll、epoll详解
- Instance "orcl", status UNKNOWN, has 1 handler(s) for this service...
- Map、Collection
- 缺省值
- Java文件IO的使用总结
- 多线程间的通信 wait()、notify()、notifyAll()
- JAVA自定义注解
- Qt中csv文件的导入与导出
- HTTP1.0、HTTP 1.1、HTTP 2.0主要区别
- uva 11134 棋盘放车,每个车游个放置范围
- spark job server原理
- Node js String Array Buffer之间相互转换
- 用忆阻器的cir文件进行pspice仿真
- Android ProgressBar直线进度条