所以我正在研究这个模拟工作日的程序,每个工作者都是自己的线程。我正在努力实施工人参加会议的会议,但会议才开始,直到应该参加会议的每个人都到了。所以我有这种方法参加会议。
public void attendMeeting(Employee worker){
this.cdStart.countDown();
worker.meetingWait();
try {
this.cdStart.await();
worker.meetingStart(this.length);
if(this.attendees.get(0).equals(worker)){
this.room.exit();
} // end if
} // end try
catch (InterruptedException err) {
// Do Nothing
} // end catch
} // end method attendMeeting
worker参数是扩展Thread的Employee类的实例,this.cdStart是CountDownLatch。但是,当与四名员工的会议一起运行时,只有一名员工似乎能够进入,减少计数,并点击await()调用。其他工作线程似乎都无法输入它。我注意到很多在线使用示例都将CountDownLock对象传递给线程本身来处理。有没有理由说这不起作用呢?
答案 0 :(得分:4)
我假设你在Employee Thread对象中有一个单独的线程传递。该单个线程将无限期地等待,直到N个参与方到达(除了Employee线程之外,您需要为每个Employee实例提供单独的线程)。这意味着如果只有一个线程持续传递Employee / Thread,那么您将永远不会在会议中等待一个以上的Employee。
此线程最多应该通知员工线程参加会议。
你应该在Meeting类中有一个锁存器并让它们等待该锁存器。这也需要对其工作方式进行轻微的重组。
您将会议实例传递给员工以使该线程等待。
public Employee extends Thread{
//define this at some point whether in constructor or a
//means of notifying the thread to attend the meeting
private Meeting meeting;
public void run(){
//do some stuff until this employee is ready to go to a meeting
meeting.waitForAllOthersToArrive();
}
}
public class Meeting{
CountDownLatch latch = new CountDownLatch(numberOfEmployees);
public void waitForAllOthersToArrive(){
latch.countDown();
latch.await();
}
}
我建议的是CylicBarrier。虽然你不会再使用它,但CyclicBarrier的工作方式更适合你想做的事情,会议类看起来像
public class Meeting{
CylicBarrier barrier = new CylicBarrier(numberOfEmployees);
public void waitForAllOthersToArrive(){
barrier.await(); //when await() is called numberOfEmployees then all waiting threads will awake
}
}