记录ThreadPoolExecutor主线程等待子线程问题

Posted Z-hhhhh

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了记录ThreadPoolExecutor主线程等待子线程问题相关的知识,希望对你有一定的参考价值。

在使用ThreadPoolExecutor启动线程池遇到一个问题:无法让主线程等待子线程完成后再继续执行。

网上找了很多方法如:
while循环进行轮询
Thread类的join方法
synchronized锁
CountDownLatch
Future
BlockingQueue
CyclicBarrier
LockSupport

最后发现都不是适用于ThreadPoolExecutor。

研究了很久才解决。

案例如下

package com.siger;

import com.google.common.util.concurrent.ThreadFactoryBuilder;

import java.util.concurrent.*;

/**
 * @author zwh
 * @date 2022/2/16
 */
public class threadTest 
    static class MyRunable implements Runnable 

        @Override
        public void run() 
            System.out.println("-------" + Thread.currentThread().getName() + "正在操作-----------");
            try 
                Thread.sleep(100);
             catch (InterruptedException e) 
                e.printStackTrace();
            
        
    


    public static void main(String[] args) throws InterruptedException 
        long startTime = System.currentTimeMillis();
        System.out.println("-------" + Thread.currentThread().getName() + "正在操作-----------");
        for (int i = 0; i < 100; i++) 
            System.out.print(i + "\\t");
        

        ThreadFactory threadFactory = new ThreadFactoryBuilder().setNameFormat("thread-call-runner-%d").build();
        ThreadPoolExecutor executor = new ThreadPoolExecutor(8, 8 + 2, 500L, TimeUnit.MICROSECONDS, new LinkedBlockingDeque<>(), threadFactory);


        for (int i = 0; i < 20; i++) 
        //*******问题的关键点******
            Future<?> future = executor.submit(new MyRunable());
            try 
                future.get();
             catch (ExecutionException e) 
                e.printStackTrace();
            
        

        executor.shutdown();
        System.out.println("-------" + Thread.currentThread().getName() + "正在操作-----------");
        for (int i = 200; i < 400; i++) 
            System.out.print(i + "\\t");
        
        long endTime = System.currentTimeMillis();
        long usedTime = (endTime - startTime) / 1000;
        System.out.println("-----------总计耗时" + usedTime + "-------------");


    


以上是我的方案,测试后顺利完成。

如果有哪位大佬有更好的方法,还请不吝赐教。

前面查的那些方法不适用ThreadPoolExecutor,这个创建方法虽然好,不容易出现OOM,可能用的还不习惯,还是要多研究研究。

关于ThreadPoolExecutor的其他问题可以看另外一篇文章
阿里巴巴提示:手动创建线程效果更好

以上是关于记录ThreadPoolExecutor主线程等待子线程问题的主要内容,如果未能解决你的问题,请参考以下文章

记录ThreadPoolExecutor主线程等待子线程问题

关于ThreadPoolExecutor线程池,该怎么处理

ThreadPoolExecutor 的基本原理

ThreadPoolExecutor 线程池

线程池ThreadPoolExecutor

深入浅出Java并发编程指南「源码分析篇」透析ThreadPoolExecutor线程池运作机制和源码体系