Java,wait,notify,notifyAll的使用方法

来源:互联网 发布:南财网络教育平台 编辑:程序博客网 时间:2024/06/05 04:17

import java.util.Date;public class NotifyTest {    private String[] flag = new String[]{"true"};    class NotifyThread extends Thread {        public NotifyThread(String name) {            super(name);            System.out.println("NotifyThread 构造函数 "+new Date());        }        public void run() {            System.out.println("NotifyThread 进入run "+new Date());            try {                System.out.println("NotifyThread 开始sleep "+new Date());                sleep(3000);//推迟3秒钟通知                System.out.println("NotifyThread 结束sleep "+new Date());            } catch (InterruptedException e) {                e.printStackTrace();            }//            flag = "false";//            flag.notify();//Exception in thread "notify01" java.lang.IllegalMonitorStateException,没有拿到flag对象的控制权,添加 synchronized (flag)//            synchronized (flag){//                flag = "false";//对在同步块中对flag进行了赋值操作,使得flag引用的对象改变,这时候再调用notify方法时,因为没有控制权所以抛出异常。//                flag.notify();//Exception in thread "notify01" java.lang.IllegalMonitorStateException//            }//             synchronized (flag){//                 flag[0] = "false";//                 flag.notify();  //只输出了一个,wait time :3001  waiter01 end waiting!//             }            synchronized (flag){                System.out.println("NotifyThread  进入synchronized  已获得flag的控制权");                flag[0] = "false";//这里的修改对程序运行不起作用                flag.notifyAll(); //三个线程都会输出                try {                    sleep(3000);                } catch (InterruptedException e) {                    e.printStackTrace();                }                System.out.println("NotifyThread  退出synchronized 已释放flag的控制权");            }            System.out.println("NotifyThread 退出run "+new Date());        }//run    };    class WaitThread extends Thread {        public WaitThread(String name) {            super(name);        }        public void run() {            synchronized (flag) { //后来添加                while (flag[0].equals("true")) {//Exception in thread "waiter01" java.lang.IllegalMonitorStateException,没有拿到flag对象的控制权,添加 synchronized (flag) {}                    System.out.println(getName() + " begin waiting!");                    long waitTime = System.currentTimeMillis();                    try {                        flag.wait();//在这里等待,暂停执行。获得控制权后才能继续执行                    } catch (InterruptedException e) {                        e.printStackTrace();                    }                    waitTime = System.currentTimeMillis() - waitTime;                    System.out.println("wait time :" + waitTime);                }                System.out.println(getName() + " end waiting!");            }        }//run    }    public static void main(String[] args) throws InterruptedException {        System.out.println("Main Thread Begin!");        NotifyTest test = new NotifyTest();        NotifyThread notifyThread = test.new NotifyThread("notify01");        WaitThread waitThread01 = test.new WaitThread("waiter01");        WaitThread waitThread02 = test.new WaitThread("waiter02");        WaitThread waitThread03 = test.new WaitThread("waiter03");        notifyThread.start();        waitThread01.start();        waitThread02.start();        waitThread03.start();        System.out.println("Main Thread End!");    }}/*Main Thread Begin!NotifyThread 构造函数 Tue Dec 05 15:44:52 CST 2017Main Thread End!waiter02 begin waiting!NotifyThread 进入run Tue Dec 05 15:44:52 CST 2017NotifyThread 开始sleep Tue Dec 05 15:44:52 CST 2017waiter03 begin waiting!waiter01 begin waiting!NotifyThread 结束sleep Tue Dec 05 15:44:55 CST 2017NotifyThread  进入synchronized  已获得flag的控制权NotifyThread  退出synchronized 已释放flag的控制权NotifyThread 退出run Tue Dec 05 15:44:58 CST 2017wait time :5978waiter01 end waiting!wait time :5981waiter03 end waiting!wait time :6001waiter02 end waiting!*/

如果对象调用了wait方法就会使持有该对象的线程把该对象的控制权交出去,然后处于等待状态。
如果对象调用了notify方法就会通知某个正在等待这个对象的控制权的线程可以继续运行。等待这个对象的控制权的线程获得控制权以后才能继续运行。
如果对象调用了notifyAll方法就会通知所有等待这个对象控制权的线程继续运行。等待这个对象的控制权的线程获得控制权以后才能继续运行。


详细可见:

http://longdick.iteye.com/blog/453615






原创粉丝点击