博客
关于我
Java线程池源码及原理
阅读量:445 次
发布时间:2019-03-06

本文共 1402 字,大约阅读时间需要 4 分钟。

线程池的状态与源码分析

1. 线程池的状态

线程池的运行状态通过 ctl 中的高3位来表示,共有5种状态:

  • RUNNING:高3位为111,线程池接收新任务。
  • SHUTDOWN:高3位为000,线程池停止接收新任务。
  • STOP:高3位为001,线程池完全终止。
  • TIDYING:高3位为010,所有任务已终止。
  • TERMINATED:高3位为011,terminated() 方法已执行完成。

线程池的核心池大小为 corePoolSize,最大允许线程数为 maximumPoolSize,线程活跃时间为 keepAliveTime


2. 任务的执行

线程池的任务执行流程分为几个关键步骤:

  • execute(Runnable command)

    • 检查当前运行线程数是否小于核心池大小 corePoolSize,如果是,则直接调用 addWorker
    • 否则,将任务添加到工作队列 workQueue 中。
    • 如果工作队列已满,则尝试再次调用 addWorker
  • addWorker(Runnable firstTask, boolean core)

    • 判断线程池状态。
    • 通过 CAS 操作增加运行线程数。
    • 创建 Worker 实例,线程通过 ThreadFactory 构造,并将 Workerrun() 方法设置为线程的初始目标。
    • 启动线程。
  • runWorker(Worker w)

    • 循环调用 getTask() 获取任务。
    • 执行任务前调用 beforeExecute 方法。
    • 执行任务后调用 afterExecute 方法。
  • getTask()

    • 通过 ctl.get() 获取当前线程池状态 c
    • 根据 runStateOf(c) 判断线程池状态:
      • 如果是 SHUTDOWNSTOP 且工作队列为空,减少运行线程数并返回 null
    • 获取当前运行线程数 wc
    • 如果是核心线程允许超时或线程数量超过最大值且工作队列为空,尝试减少运行线程数并返回 null
    • 从工作队列中获取任务。如果任务存在,返回任务;否则,等待队列中的任务。

  • 3. 任务执行,带返回值的

    线程池支持带返回值的任务执行,主要通过 Future 实现。具体方法如下:

    public Future
    submit(Callable
    task) { if (task == null) throw new NullPointerException(); RunnableFuture
    ftask = newTaskFor(task); execute(ftask); return ftask;}public Future
    submit(Runnable task) { if (task == null) throw new NullPointerException(); RunnableFuture
    ftask = newTaskFor(task, null); execute(ftask); return ftask;}
    • 将任务封装到 RunnableFuture 中,并通过 execute 方法提交执行。
    • RunnableFuture 实现了 Future 接口,可以用来获取任务的执行结果。

    参考资料

    转载地址:http://boufz.baihongyu.com/

    你可能感兴趣的文章
    ntp server 用法小结
    查看>>
    ntpdate 通过外网同步时间
    查看>>
    ntpdate同步配置文件调整详解
    查看>>
    NTPD使用/etc/ntp.conf配置时钟同步详解
    查看>>
    NTP及Chrony时间同步服务设置
    查看>>
    NTP服务器
    查看>>
    NTP配置
    查看>>
    NUC1077 Humble Numbers【数学计算+打表】
    查看>>
    NuGet Gallery 开源项目快速入门指南
    查看>>
    NuGet(微软.NET开发平台的软件包管理工具)在VisualStudio中的安装的使用
    查看>>
    nuget.org 无法加载源 https://api.nuget.org/v3/index.json 的服务索引
    查看>>
    Nuget~管理自己的包包
    查看>>
    NuGet学习笔记001---了解使用NuGet给net快速获取引用
    查看>>
    nullnullHuge Pages
    查看>>
    NullPointerException Cannot invoke setSkipOutputConversion(boolean) because functionToInvoke is null
    查看>>
    null可以转换成任意非基本类型(int/short/long/float/boolean/byte/double/char以外)
    查看>>
    Number Sequence(kmp算法)
    查看>>
    Numix Core 开源项目教程
    查看>>
    numpy
    查看>>
    Numpy 入门
    查看>>