IllegalMonitorStateException - CyclicBarrier

时间:2010-12-03 13:49:41

标签: java spring concurrency spring-mvc

我有一个使用CyclicBarrier的方法,如下所示:

public void getMessage(Message obj){
    CyclicBarrier barrier = new CyclicBarrier(1, new Runnable() {
        @Override
        public void run() {
            synchronized(obj){ 
                System.out.println("--The End --");
            }
        }
    });

    executor.execute(new Runnable() {
        @Override
        public void run() {
            synchronized(obj){
                //Perform some routine with message object
            }
            try {
                barrier.wait();//java.lang.IllegalMonitorStateException thrown on this line
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    });
}

在我等待例程完成执行的那一刻,我得到:

Exception in thread "pool-2-thread-3"
java.lang.IllegalMonitorStateException
    at java.lang.Object.wait(Native Method)
    at java.lang.Object.wait(Object.java:502)

有谁知道我在这里做错了什么?

5 个答案:

答案 0 :(得分:4)

为了在任何对象上调用wait(),当前线程必须拥有其监视器。您在没有任何barrier.wait()的情况下致电synchronized(barrier)

但是,您可能打算使用await()方法(在CyclicBarrier上)而不是wait()。这很难说,因为目前还不清楚你想要达到的目标。

答案 1 :(得分:0)

是的,你需要像这样获得屏障的监视器:

synchhronized(barrier){
try {
     barrier.wait();//java.lang.IllegalMonitorStateException not thrown on this line
    } catch (InterruptedException e) {
    e.printStackTrace();
}
}

答案 2 :(得分:0)

也许您确实希望使用await()代替wait()

wait用于阻止特定对象上的线程,它是每个对象的一个​​特性,但在您的情况下,您在不使用它的监视器的情况下调用它。您应该从相同的对象内部致电wait,或者使用synchronized阻止barrier本身。{/ p>

答案 3 :(得分:0)

您需要在使用屏障对象之前获取锁定。

此致 Dheeraj Joshi

答案 4 :(得分:0)

不打算像在这里那样使用cyclicBarrier:参与的线程应该调用阻塞“await()”方法。

作为旁注,计数为1的CyclicBarrier完全没用:它的目的是允许一定数量的线程(屏障计数)在继续之前等待彼此。 也许您应该考虑更改整个算法,特别是如果您不确定并发内容的工作原理。