我对Java Multithreading非常陌生。尝试在Java线程中学习计数锁存和执行程序,并实现了以下代码-
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class ExecutorBasicFramework {
class MyThread extends Thread{
int iCount ; String name;
CountDownLatch latch;
public MyThread(int iCount, String name, CountDownLatch latch) {
super();
this.iCount = iCount;
this.name = name;
this.latch = latch;
}
@Override
public void run() {
for(int i=0;i<10;i++){
System.out.println(name+" Printing .... "+ ++iCount+" L "+latch.getCount());
try {
Thread.sleep(100);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
latch.countDown();
}
}
public ExecutorBasicFramework() {
createThread();
}
private void createThread() {
ExecutorService exec = Executors.newFixedThreadPool(10);
CountDownLatch latch = new CountDownLatch(10);
for(int i=0;i<10;i++){
MyThread thread = new MyThread(i*10, ""+i,latch);
exec.execute(thread);
try {
latch.await();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
exec.shutdownNow();
}
public static void main(String[] args) {
new ExecutorBasicFramework();
}
}接下来的产出是-
0 Printing .... 1 L 10
0 Printing .... 2 L 10
0 Printing .... 3 L 10
0 Printing .... 4 L 10
0 Printing .... 5 L 10
0 Printing .... 6 L 10
0 Printing .... 7 L 10
0 Printing .... 8 L 10
0 Printing .... 9 L 10
0 Printing .... 10 L 10然后流动就像继续等待。我的预期输出和上面一样,但是在打印0之后,它应该在1到9之间打印类似的输出,然后程序应该停止。
我认为计数锁定是等待和等待,它不会增加下一个计数器的执行者。所以我无法得到预期的输出。我期待着产出就像-
0 Printing .... 1 L 10
0 Printing .... 2 L 10
0 Printing .... 3 L 10
0 Printing .... 4 L 10
0 Printing .... 5 L 10
0 Printing .... 6 L 10
0 Printing .... 7 L 10
0 Printing .... 8 L 10
0 Printing .... 9 L 10
0 Printing .... 10 L 10
1 Printing .... 11 L 9
1 Printing .... 12 L 9
1 Printing .... 13 L 9
1 Printing .... 14 L 9
1 Printing .... 15 L 9
1 Printing .... 16 L 9
1 Printing .... 17 L 9
1 Printing .... 18 L 9
1 Printing .... 19 L 9
1 Printing .... 20 L 9
and So on ...
2 Printing .... 21 L 8
2 Printing .... 22 L 8
2 Printing .... 23 L 8对于锁存的每个递减计数器,下一个线程池必须执行一个计数到10。然后,它必须再次减少锁存计数器,并且进程再次重复,直到线程9完成相同的操作。
请提出一些建议。
发布于 2013-02-26 20:17:10
如果您打算使用CountDownLatch让main()方法等待所有线程的执行,那么您应该将latch.await()移到提交线程的循环之外。另外,在不再次设置中断标志的情况下,您不应该吃InterruptedException。(见本文)。
修正后的结果如下:
for(int i=0;i<10;i++){
MyThread thread = new MyThread(i*10, ""+i,latch);
exec.execute(thread);
}
try {
latch.await();
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}虽然这肯定会起作用,但在使用ExecutorService时,Latch是等待在另一个线程上运行的可运行线程的次优方式。如果使用submit()而不是execute(),则可以使用submit()返回的Future通过调用提交的Runnable来等待提交Runnable的完成。
发布于 2013-02-26 17:39:13
因此,您正在配置一个10 new CountDownLatch(10)的倒计时值,但是您的代码只会在每个线程中减少一次。当你只分了一个线程后,你就会等待锁锁,但它是在9点。
MyThread thread = new MyThread(i*10, ""+i,latch);
exec.execute(thread);
latch.await();不确定您的意图是什么,但也许latch.countDown();应该在线程中的for循环中呢?
for(int i=0;i<10;i++) {
...
// if you want the latch to count-down 10 times, it should be inside the loop
latch.countDown();
}
// it should not go here, outside the loop如果目标是等待所有作业完成,则可以使用ExecutorService.awaitTermination(...)方法来完成:
// submit jobs in loop
exec.shutdown();
exec.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);另外,您不应该在您的Thread类中扩展MyThread。您应该实现Runnable。代码工作的唯一原因是Thread也实现了Runnable,但是MyThread不应该是Thread。ExecutorService采用Runnable或Callable,而不是Thread。它在服务内部为您管理线程。
发布于 2013-02-27 15:27:24
谢谢大家的投入。我找到了一个更简单的解决方案来达到我的期望。我只是使用了Executors.newSingleThreadExecutor();,因为它已经确保了所有任务都将被保证按顺序执行。
https://stackoverflow.com/questions/15095582
复制相似问题