0

我有以下代码来启动在队列对象上同步的 3 个线程(在构造时传递)。每个线程都尝试从队列中读取以执行操作:

class smokers extends Thread{

    final Queue q;
    boolean smoked=false;

    public smokers(Queue q,restype res){
        this.q=q;
            ....
    }

    public void run(){

        try{
            while(smoked==false){
                synchronized(q){
                    if (q.size()==0) wait();
                                    ...
                        q.poll();
                    notify();
                    }
                }
            }
        }catch (InterruptedException intEx)
        {
            intEx.printStackTrace();
        }

    }

    public static void main(String[] args){
        final Queue q=new LinkedList();
        ....
            while (q.size()<10){
            q.add(....);
        }
        smokers[] smokers=new smokers[3];
        smokers[0]=new smokers(q,restype.TOBACCO);
        smokers[1]=new smokers(q,restype.PAPER);
        smokers[2]=new smokers(q,restype.MATCH);

        // Start the smokers
        for (int i = 0; i < 3; i++) {
              smokers[i].start();
        }


        // Wait for them to finish
        for (int i = 0; i < 3; i++) {
          try {
            smokers[i].join();
          } catch(InterruptedException ex) { }
        }

        // All done
        System.out.println("Done");
    }

}

我得到以下信息:

Exception in thread "Thread-2" Exception in thread "Thread-1" java.lang.IllegalMonitorStateException
        at java.lang.Object.notify(Native Method)
        at com.bac.threads.smokers.run(smokers.java:35)
Exception in thread "Thread-0" java.lang.IllegalMonitorStateException
        at java.lang.Object.notify(Native Method)
        at com.bac.threads.smokers.run(smokers.java:35)
java.lang.IllegalMonitorStateException
        at java.lang.Object.notify(Native Method)
        at com.bac.threads.smokers.run(smokers.java:35)

我究竟做错了什么?

4

2 回答 2

3

你打电话notifythis但你在现场同步q。通话也一样wait

于 2012-10-10T10:05:42.797 回答
2

您在与您锁定的对象不同的对象上调用 notify()。

notify();

是相同的

this.notify();

当你打算

q.notify();

顺便说一句:我会看看高级并发库

于 2012-10-10T10:05:05.427 回答