ThreadPool

https://snailclimb.gitee.io/javaguide/#/./docs/java/Multithread/java%E7%BA%BF%E7%A8%8B%E6%B1%A0%E5%AD%A6%E4%B9%A0%E6%80%BB%E7%BB%93?id=%e4%ba%8c-executor-%e6%a1%86%e6%9e%b6

优点:

  • 降低资源消耗。通过重复利用已创建的线程降低线程创建和销毁造成的消耗。
  • 提高响应速度。当任务到达时,任务可以不需要的等到线程创建就能立即执行。
  • 提高线程的可管理性。

池化技术相比大家已经屡见不鲜了,线程池、数据库连接池、Http 连接池等等都是对这个思想的应用。池化技术的思想主要是为了减少每次获取资源的消耗,提高对资源的利用率。

Executor

Executor框架是 Java5 之后引进的,在 Java 5 之后,通过 Executor 来启动线程比使用 Thread 的 start 方法更好,除了更易管理,效率更好(用线程池实现,节约开销)外,还有关键的一点:有助于避免 this 逃逸问题

Executor 框架不仅包括了线程池的管理,还提供了线程工厂、队列以及拒绝策略等,Executor 框架让并发编程变得更加简单。
在这里插入图片描述

任务(Runnable /Callable)

执行任务需要实现的 Runnable 接口 或 Callable接口。Runnable 接口或 Callable 接口 实现类都可以被 ThreadPoolExecutor 或 ScheduledThreadPoolExecutor 执行。

任务的执行(Executor)

任务执行机制的核心接口 Executor ,以及继承自 Executor 接口的 ExecutorService 接口。ThreadPoolExecutor 和 ScheduledThreadPoolExecutor 这两个关键类实现了 ExecutorService 接口。

这里提了很多底层的类关系,但是,实际上我们需要更多关注的是 ThreadPoolExecutor 这个类,这个类在我们实际使用线程池的过程中,使用频率还是非常高的。

线程池,Executor,Executors,ExecutorService,CompletionService,Future,Callable等。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-d9nQT9Vp-1590499690926)(55126EECF1AC4B1D9430CD2BCEFD7E62)]

创建线程池

一. ThreadPoolExecutor构造函数

ThreadPoolExecutor 类分析

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-I6eeVXPv-1590499690929)(F2D0189D8E3E48968A054C2805346D09)]

ThreadPoolExecutor类的四种构造方式;[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-s8H6WdMc-1590499690931)(97D74078CAA5493EB765C1B577D688B2)]

    /**
     * 用给定的初始参数创建一个新的ThreadPoolExecutor。
     */
    public ThreadPoolExecutor(int corePoolSize,//线程池的核心线程数量
                              int maximumPoolSize,//线程池的最大线程数
                              long keepAliveTime,//当线程数大于核心线程数时,多余的空闲线程存活的最长时间
                              TimeUnit unit,//时间单位
                              BlockingQueue<Runnable> workQueue,//任务队列,用来储存等待执行任务的队列
                              ThreadFactory threadFactory,//线程工厂,用来创建线程,一般默认即可
                              RejectedExecutionHandler handler//拒绝策略,当提交的任务过多而不能及时处理时,我们可以定制策略来处理任务
                               ) {
.execute()方法调用流程
public void execute(Runnable command) {
    if (command == null)
        throw new NullPointerException();
    //获得当前线程池
    int c = ctl.get();
    //判断线程数是否否有空余的
    if (workerCountOf(c) < corePoolSize) {
    //创建内部工作类,执行command
        if (addWorker(command, true))
            return;
        c = ctl.get();//返回当前线程池
    }
    //还有位置,判断队列是否满了并且推入
    if (isRunning(c) && workQueue.offer(command)) {
        int recheck = ctl.get();
        //再次判断,双重检查
        if (! isRunning(recheck) && remove(command))
            reject(command);
        else if (workerCountOf(recheck) == 0)
            addWorker(null, false);
    }
    else if (!addWorker(command, false))
        //拒绝任务
        reject(command);
}

addWorker创建内部Worker类,其中调用getThreadFactory().newThread(this)来创建执行自己的线程,之后在addWorker中start该线程

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5FQCgNDB-1590499690932)(D99AC9E3EBEA45478B44451CD4E91275)]

二. 通过 Executor 框架的工具类 Executors 来实现 我们可以创建三种类型的 ThreadPoolExecutor

  • newCachedThreadPool: 创建一个可缓存线程池,如果线程池长度超过处理需要,可灵活回收空闲线程,若无可回收,则新建线程。
  • newFixedThreadPool: 创建一个定长线程池,可控制线程最大并发数,超出的线程会在队列中等待。
  • newSingleThreadExecutor: 创建一个单线程化的线程池,它只会用唯一的工作线程来执行任务,保证所有任务按照指定顺序(FIFO, LIFO, 优先级)执行

返回的是 “ExecutorService”;
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-55o81DmQ-1590499690933)(D128FAD484A14E2F92D1DFCEC535300D)]

  • newScheduledThreadPool: 创建一个定长线程池,支持定时及周期性任务执行。

返回的是 “ScheduledExecutorService”;

public class NewScheduledThreadPool {
    /**
     * 我们获取四次次线程,观察4个线程地址
     * @param args
     */
    public static  void main(String[]args)
    {
        ScheduledExecutorService newScheduledThreadPool = Executors.newScheduledThreadPool(2);
        System.out.println("****************************newFixedThreadPool*******************************");
        for(int i=0;i<4;i++)
        {
            final int index=i;
            //延迟三秒执行
            newScheduledThreadPool.schedule(new ThreadForpools(index),3, TimeUnit.SECONDS);
        }
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值