I'm trying to implement some logic when I 开发者_运维问答create main(father) thread witch executes several other threads. Then it waits for some condition which child threads creates. After condition is meet the father executes some more child threads. The problem that when I use wait/notify I have java.lang.IllegalMonitorStateException exception. Here is the code:
public class MyExecutor {
final static ArrayBlockingQueue<Runnable> queue = new ArrayBlockingQueue<Runnable>(10);
final static ExecutorService svc = Executors.newFixedThreadPool(1);
static final ThreadPoolExecutor threadPool = new ThreadPoolExecutor(5, 8, 10, TimeUnit.SECONDS, queue);
public static void main(String[] args) throws InterruptedException {
final MyExecutor me = new MyExecutor();
svc.execute(new Runnable() {
public void run() {
try {
System.out.println("Main Thread");
me.execute(threadPool, 1);
System.out.println("Main Thread waiting");
wait();
System.out.println("Main Thread notified");
me.execute(threadPool, 2);
Thread.sleep(100);
threadPool.shutdown();
threadPool.awaitTermination(20000, TimeUnit.SECONDS);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
svc.shutdown();
svc.awaitTermination(10000, TimeUnit.SECONDS);
System.out.println("Main Thread finished");
}
public void execute(ThreadPoolExecutor tpe, final int id) {
tpe.execute(new Runnable() {
public void run() {
try {
System.out.println("Child Thread " + id);
Thread.sleep(2000);
System.out.println("Child Thread " + id + " finished");
notify();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
}
}
When I comment wait and notify line I have the following output:
Main Thread Main Thread waiting Main Thread notified Child Thread 1 Child Thread 2 Child Thread 1 finished Child Thread 2 finished Main Thread finishedThere is a series of design flaws in your code:
Calling both wait()
and notify()
must occur only when you are the owner of the lock of the object:
synchronized(foo) {
foo.wait();
}
You are calling wait()
and notify()
on different objects (inner classes!) - if one threads is waiting on one object, you must call notify
on the same object.
There is a possibility of missed notify
when this:
me.execute(threadPool, 1);
is called before wait
- very serious bug (race condition possibility).
Others might suggest you using some higher level synchronization methods, but it is crucial to understand the basics.
精彩评论