• 线程池介绍及用法


    一、概念:

    提供一组线程,让这些线程来执行各个任务,每执行一个任务便会用一个线程。线程池可以便于重复利用线程、便于统一管理线程

    二、jdk提供的线程池api:

    1、ExecutorService

    真正的线程池接口,有子类ThreadPoolExecutor

    2、Executors:

    工具类、工厂类。用于创建各种不同类型的线程池(定长、单一、缓存、定时及周期性),指向给ExecutorService。底层都是对ThreadPoolExecutor的构造方法进行封装。

    详情见:https://blog.csdn.net/csucsgoat/article/details/124139094

    三、ThreadPoolExecutor

    1、五个核心构造参数

    /**
     * corePoolSize    核心线程数(线程池刚实例化时就初始化的线程数)
     * maximumPoolSize 线程池中允许的最大线程数量
     * keepAliveTime   非核心线程处于空间状态存在时间
     * unit            keepAliveTime 的时间单位
     * workQueue       用来储存等待执行任务的队列
     */
    public ThreadPoolExecutor(int corePoolSize,
                              int maximumPoolSize,
                              long keepAliveTime,
                              TimeUnit unit,
                              BlockingQueue<Runnable> workQueue) {
        this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
             Executors.defaultThreadFactory(), defaultHandler);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    2、常用的执行命令

    void execute(Runnable command);  //参数是Runnable ,无返回值
    
    Future<?> submit(Runnable task);  //参数可以是Runnable、Callable,有返回值
    
    • 1
    • 2
    • 3

    3、常用的关闭命令

    如果使用的线程池核心线程数不为0,建议在使用完后将线程池关闭。因为核心线程会占用内存资源

    //用此方法后继续提交新任务会抛异常,等待队列中的任务任然继续执行,正在执行的任务不会被中断
    void shutdown();  
    
    //用此方法后继续提交新任务会抛异常,等待队列中的任务不会继续执行并且队列中没执行的任务会返回给list,正在执行的任务会被中断
    List<Runnable> shutdownNow();  
    
    • 1
    • 2
    • 3
    • 4
    • 5

    详情见:https://blog.csdn.net/qq_36691683/article/details/84856516

    四、线程池工作流程

    在这里插入图片描述

    五、简单代码样例

    public String testExecutor() throws InterruptedException {
    
        ExecutorService service = new ThreadPoolExecutor(
                100,
                150,
                0L,
                TimeUnit.MILLISECONDS,
                new LinkedBlockingQueue<>(20480000)
        );
        CountDownLatch cdl = new CountDownLatch(100);
    
        for (int i=0;i<100;i++){
            Runnable runnable = new Runnable() {
                @Override
                public void run() {
                    //执行业务逻辑
    
                    System.err.println("线程"+Thread.currentThread().getName()+"执行完");
    
                    //计数器递减
                    cdl.countDown();
                }
            };
    
    
            service.execute(runnable);
        }
    
    
        //线程执行完后再执行主线程
        cdl.await();
    
        //关闭线程池释放资源
        service.shutdown();
    
        return "ok";
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
  • 相关阅读:
    洛谷刷题C语言:询问、光图、苏联人、Another Cow Number Game G、STROJOPIS
    浅谈pytorch安装
    【译】.NET 7 中的性能改进(九)
    ThreadLocal类
    2022年最新贵州建筑安全员模拟题库及答案
    Java并发编程学习7-阻塞队列
    Java线程池源码解析
    文盘 Rust -- tokio 绑定 cpu 实践
    反渗透水处理成套设备有哪些
    口袋参谋:如何一键获取竞品数据?这招实用!
  • 原文地址:https://blog.csdn.net/qq_38639813/article/details/126845568