我是靠谱客的博主 现代手链,最近开发中收集的这篇文章主要介绍java异步多线程 判断线程状态_判断线程池中的线程是否全部执行完毕,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

在使用多线程的时候有时候我们会使用 java.util.concurrent.Executors的线程池,当多个线程异步执行的时候,我们往往不好判断是否线程池中所有的子线程都已经执行完毕,但有时候这种判断却很有用,例如我有个方法的功能是往一个文件异步地写入内容,我需要在所有的子线程写入完毕后在文件末尾写“---END---”及关闭文件流等,这个时候我就需要某个标志位可以告诉我是否线程池中所有的子线程都已经执行完毕,我使用这种方式来判断。

1 public classMySemaphore {2

3 public static void main(String[] args) throwsIOException, InterruptedException {4 final File stream = new File("c:\temp\stonefeng\stream.txt");5 final OutputStream os = newFileOutputStream(stream);6 final OutputStreamWriter writer = newOutputStreamWriter(os);7 final Semaphore semaphore = new Semaphore(10);8 ExecutorService exec =Executors.newCachedThreadPool();9

10 final long start =System.currentTimeMillis();11 for (int i = 0; i < 10000000; i++) {12 final int num =i;13 Runnable task = newRunnable() {14 @Override15 public voidrun() {16 try{17 semaphore.acquire();18 writer.write(String.valueOf(num)+"n");19 semaphore.release();20 } catch(IOException e) {21 e.printStackTrace();22 } catch(InterruptedException e) {23 e.printStackTrace();24 }25 }26 };27 exec.submit(task);28 }29 exec.shutdown();30 while(true){31 if(exec.isTerminated()){32 writer.write("---END---n");33 writer.close();34 System.out.println("所有的子线程都结束了!");35 break;36 }37 Thread.sleep(1000);38 }39 final long end =System.currentTimeMillis();40 System.out.println((end-start)/1000);41 }42 }

当调用ExecutorService.shutdown方法的时候,线程池不再接收任何新任务,但此时线程池并不会立刻退出,直到添加到线程池中的任务都已经处理完成,才会退出。在调用shutdown方法后我们可以在一个死循环里面用isTerminated方法判断是否线程池中的所有线程已经执行完毕,如果子线程都结束了,我们就可以做关闭流等后续操作了。

判断线程池中的线程是否全部执行完毕的另外一种解决方案则是使用闭锁(CountDownLatch)来实现,CountDownLatch是一种灵活的闭锁实现,它可以使一个或多个线程等待一组事件发生。闭锁状态包括一个计数器,该计数器被初始化为一个正数,表示需要等待的事件数量。countDown方法递减计数器,表示有一个事件已经发生了,而await方法等待计数器达到零,即表示需要等待的事情都已经发生。可以使用闭锁来这样设计程序达到目的:

1 public classCountDownLatchApproach {2 public static void main(String[] args) throwsIOException, InterruptedException {3 final int nThreads = 10;4 final CountDownLatch endGate = newCountDownLatch(nThreads);5 final File stream = new File("c:\temp\stonefeng\stream.txt");6 final OutputStream os = newFileOutputStream(stream);7 final OutputStreamWriter writer = newOutputStreamWriter(os);8 ExecutorService exec =Executors.newCachedThreadPool();9 for (int i = 0; i < nThreads; i++) {10 final int num =i;11 Runnable task = newRunnable() {12 @Override13 public voidrun() {14 try{15 writer.write(String.valueOf(num)+"n");16 } catch(IOException e) {17 e.printStackTrace();18 } finally{19 endGate.countDown();20 }21 }22 };23 exec.submit(task);24 }25 endGate.await();26 writer.write("---END---n");27 writer.close();28 }29 }

这种解决方案虽然可以达到目的但是性能差到没朋友,我更倾向于使用第一种方案。

现在我们有了更优雅的第三种方案,它的执行性能也不错。

1 public classMySemaphore {2

3 public static void main(String[] args) throwsIOException, InterruptedException {4 final File stream = new File("c:\temp\stonefeng\stream.txt");5 final OutputStream os = newFileOutputStream(stream);6 final OutputStreamWriter writer = newOutputStreamWriter(os);7 final Semaphore semaphore = new Semaphore(10);8 ExecutorService exec =Executors.newCachedThreadPool();9

10 final long start =System.currentTimeMillis();11 for (int i = 0; i < 10000000; i++) {12 final int num =i;13 Runnable task = newRunnable() {14 @Override15 public voidrun() {16 try{17 semaphore.acquire();18 writer.write(String.valueOf(num)+"n");19 semaphore.release();20 } catch(IOException e) {21 e.printStackTrace();22 } catch(InterruptedException e) {23 e.printStackTrace();24 }25 }26 };27 exec.submit(task);28 }29 exec.shutdown();30 exec.awaitTermination(1, TimeUnit.HOURS);31 writer.write("---END---n");32 writer.close();33 System.out.println("ËùÓеÄ×ÓÏ̶߳¼½áÊøÁË£¡");34 final long end =System.currentTimeMillis();35 System.out.println((end-start)/1000);36 }37 }

最后

以上就是现代手链为你收集整理的java异步多线程 判断线程状态_判断线程池中的线程是否全部执行完毕的全部内容,希望文章能够帮你解决java异步多线程 判断线程状态_判断线程池中的线程是否全部执行完毕所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(45)

评论列表共有 0 条评论

立即
投稿
返回
顶部