(原创)Java多线程作业题报java.lang.IllegalMonitorStateException解决

作业:

  有一个水池,水池容量500L,一边为进水口,一边为出水口,要求进水放水不能同时进行,水池一旦满了不能继续注水,一旦空了,不能继续放水,进水速度5L/s,放水速度2L/s。

  这是我学多线程时做的一道练习题,刚开始对wait()方法存在错误理解导致运行时报异常-----java.lang.IllegalMonitorStateException,修复后,在此把错误写法以及最终正确写法都整理出来。

 

class Water{

            static int litre = 500;

            boolean flag=true; //false为可以继续加水,true为可以继续放水

}

 

 class OutPour extends Thread{ //出水类

            Water w;

           

            OutPour(Water w){

                        this.w=w;

            }

           

            @Override

            public void run() { //正确写法

                        while(true){

                                   

                                    synchronized(w){

                                                if(w.flag==true){ //放水,2L/s

                                                            try {

                                                                        Thread.sleep(60);

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }

                                                            w.litre=w.litre-2;

                                                            System.out.println("放水中,现在还剩"+w.litre+"升水!");

                                                            if(w.litre<=0){ //放空了

                                                                        w.flag=false;

                                                                        System.out.println("--------空了!--------");

                                                                        w.notify();

                                                            }

                                                }else{

                                                            try {

                                                                        w.wait();//等加满

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }                      

                                                 }

                                    }

                        }

            }

/*

            @Override

            public void run() { //错误写法

                        while(true){

                                    if(w.flag==true){ //放水,2L/s

                                                synchronized(w){

                                                            try {

                                                                        Thread.sleep(60);

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }

                                                            w.litre=w.litre-2;

                                                            System.out.println("放水中,现在还剩"+w.litre+"升水!");

                                                            if(w.litre<=0){ //放空了

                                                                        w.flag=false;

                                                                        System.out.println("--------空了!--------");

                                                                        w.notify

                                                            }

                                                }

                                    }else{

                                                            try {

                                                                        w.wait();//等加满

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }

                                               

                        }

                                                   }

            }

            */

}

 

class InPour extends Thread{ //进水类

            Water w;

           

            InPour(Water w){

                        this.w=w;

            }

           

            @Override

            public void run() { //正确写法

                        while(true){

                                    synchronized(w){

                                    if(w.flag==false){//加水,5L/s

                                                            try {

                                                                        Thread.sleep(60);

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }

                                                            w.litre=w.litre+5;

                                                            System.out.println("加水中,现在有"+w.litre+"升水!");

                                                            if(w.litre>=500){//加满了

                                                                        System.out.println("-------满了!-------");

                                                                        w.flag=true;

                                                                        w.notify();

                                                            }

                                    }else{

                                                try {

                                                            w.wait();

                                                } catch (InterruptedException e) {

                                                            e.printStackTrace();

                                                }

                                    }

                                    }

}

}

            /*

            @Override

            public void run() { //错误写法

                        while(true){

                                    if(w.flag==false){ //加水,5L/s

                                                synchronized(w){

                                                            try {

                                                                        Thread.sleep(60);

                                                            } catch (InterruptedException e) {

                                                                        e.printStackTrace();

                                                            }

                                                            w.litre=w.litre+5;

                                                            if(w.litre>=500){ //加满了

                                                                        System.out.println("-------满了!-------");

                                                                        w.flag=true;

                                                                        w.notifyAll();

                                                            }

                                                }          

                                    }else{

                                                try {

                                                            w.wait();

                                                } catch (InterruptedException e) {

                                                            e.printStackTrace();

                                                }

                                    }

                        }

                       

            }

            */

}

 

 

public class Demo11 {

           

            public static void main(String[] args){

                        Water w = new Water();

                       

                        OutPour o = new OutPour(w);

                        InPour i = new InPour(w);

                       

                        o.start();

                        i.start();

            }

 

}

   run方法在业务逻辑上并没有错,报异常java.lang.IllegalMonitorStateException,是因为wait()方法必须要放在同步代码块中才能使用。把else{}语句也圈到synchronized代码块即可。也奉劝,先把笔记看了之后再敲代码,能为调试省不少时间。。。

posted on 2017-02-09 22:03  X强人艺  阅读(2270)  评论(0编辑  收藏  举报