程序是这样的
/* 第一个类*/
public class ThreadB extends Thread{
int total;
public void run(){
synchronized(this){
for(int i=0;i<101;i++){
total+=i;
}
try {
sleep(100);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
notify();
}
}
public int getTotal(){
return this.total;
}
}
/* 第二个类*/
public class ReaderResult extends Thread{
ThreadB c;
public ReaderResult(ThreadB c){
this.c=c;
}
public void run(){
synchronized (c) {
try{
System.out.println(Thread.currentThread()+"等待计算结果。。。。");
c.wait();
}catch(InterruptedException e){
e.printStackTrace();
}
System.out.println(Thread.currentThread()+"计算结果为:"+c.getTotal());
}
}
public static void main(String[] args) {
ThreadB calculator = new ThreadB();
ReaderResult reader1=new ReaderResult(calculator);
ReaderResult reader2=new ReaderResult(calculator);
ReaderResult reader3=new ReaderResult(calculator);
reader1.start();
reader2.start();
reader3.start();
calculator.start();
}
}
输出结果大多数都
Thread[Thread-1,5,main]等待计算结果。。。。
Thread[Thread-3,5,main]等待计算结果。。。。
Thread[Thread-2,5,main]等待计算结果。。。。
Thread[Thread-1,5,main]计算结果为:5050
Thread[Thread-2,5,main]计算结果为:5050
Thread[Thread-3,5,main]计算结果为:5050
理论上不是只能唤醒一个吗?
参考:http://www.iteye.com/problems/89570
你这三个wait中锁的对象是三个不同的对象,这三个虽然他们有相同的名字但是却是三个不同的ReaderResult类中的,而且你再唤醒的时候也是在他们本身内部唤醒,根据以上两点,导致你的notify唤醒没有达到预想结果。可以尝试将 ThreadB c;换成static而且将notify函数放在单独一个线程而不是在他们被wait的线程中。
notify是只能唤醒一个线程没错,但是你应该看清楚解释,当线程被wait时要有个对象,或者锁去调用这个方法,同理notify时,也是这样。而且notify的调用对象是调用wait方法时的对象,它会从等待队列中将其唤醒。你注意代码,你三个线程调用wait方法的对象是同一个对象,那么应该会导致一次notify唤醒三个。