Java中ThreadPoolExecutor的参数理解

本文详细介绍了如何使用Java的Executors工具类和ThreadPoolExecutor接口创建不同类型的线程池,包括固定大小线程池、单线程池、可缓冲线程池,以及如何配置线程池参数以优化线程执行效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、使用Executors创建线程池    

        之前创建线程的时候都是用的Executors的newFixedThreadPool(),newSingleThreadExecutor(),newCachedThreadPool()这三个方法。当然Executors也是用不同的参数去new ThreadPoolExecutor

    1. newFixedThreadPool()

    创建线程数固定大小的线程池。 由于使用了LinkedBlockingQueue所以maximumPoolSize 没用,当corePoolSize满了之后就加入到LinkedBlockingQueue队列中。每当某个线程执行完成之后就从LinkedBlockingQueue队列中取一个。所以这个是创建固定大小的线程池。

  public  static  ExecutorService newFixedThreadPool( int  nThreads) {
         return  new  ThreadPoolExecutor(nThreads, nThreads,
                                       0L, TimeUnit.MILLISECONDS,
                                       new  LinkedBlockingQueue<Runnable>());
     }
  public  ThreadPoolExecutor( int  corePoolSize,
                               int  maximumPoolSize,
                               long  keepAliveTime,
                               TimeUnit unit,
                               BlockingQueue<Runnable> workQueue) {
       this (corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
              Executors.defaultThreadFactory(), defaultHandler);
     }

 2.newSingleThreadPool()

    创建线程数为1的线程池,由于使用了LinkedBlockingQueue所以maximumPoolSize 没用,corePoolSize为1表示线程数大小为1,满了就放入队列中,执行完了就从队列取一个。

  public  static  ExecutorService newSingleThreadExecutor() {
         return  new  FinalizableDelegatedExecutorService
             ( new  ThreadPoolExecutor( 1 1 ,
                                     0L, TimeUnit.MILLISECONDS,
                                     new  LinkedBlockingQueue<Runnable>()));
     }

  3.newCachedThreadPool()

    创建可缓冲的线程池。没有大小限制。由于corePoolSize为0所以任务会放入SynchronousQueue队列中,SynchronousQueue只能存放大小为1,所以会立刻新起线程,由于maxumumPoolSize为Integer.MAX_VALUE所以可以认为大小为2147483647。受内存大小限制。

  public  static  ExecutorService newCachedThreadPool() {
         return  new  ThreadPoolExecutor( 0 , Integer.MAX_VALUE,
                                       60L, TimeUnit.SECONDS,
                                       new  SynchronousQueue<Runnable>());
     }
public  ThreadPoolExecutor( int  corePoolSize,
                           int  maximumPoolSize,
                           long  keepAliveTime,
                           TimeUnit unit,
                           BlockingQueue<Runnable> workQueue) {
         this (corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
              Executors.defaultThreadFactory(), defaultHandler);
     }

    

二、使用ThreadPoolExecutor创建线程池

ThreadPoolExecutor的构造函数

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
   public  ThreadPoolExecutor( int  corePoolSize,
                               int  maximumPoolSize,
                               long  keepAliveTime,
                               TimeUnit unit,
                               BlockingQueue<Runnable> workQueue,
                               ThreadFactory threadFactory,
                               RejectedExecutionHandler handler) {
         if  (corePoolSize <  0  ||
             maximumPoolSize <=  0  ||
             maximumPoolSize < corePoolSize ||
             keepAliveTime <  0 )
             throw  new  IllegalArgumentException();
         if  (workQueue ==  null  || threadFactory ==  null  || handler ==  null )
             throw  new  NullPointerException();
         this .corePoolSize = corePoolSize;
         this .maximumPoolSize = maximumPoolSize;
         this .workQueue = workQueue;
         this .keepAliveTime = unit.toNanos(keepAliveTime);
         this .threadFactory = threadFactory;
         this .handler = handler;
     }
参数:

 1、corePoolSize核心线程数大小,当线程数<corePoolSize ,会创建线程执行runnable

        2、maximumPoolSize 最大线程数, 当线程数 >= corePoolSize的时候,会把runnable放入workQueue中

        3、keepAliveTime  保持存活时间,当线程数大于corePoolSize的空闲线程能保持的最大时间。

        4、unit 时间单位

        5、workQueue 保存任务的阻塞队列

        6、threadFactory 创建线程的工厂

        7、handler 拒绝策略

任务执行顺序:

        1、当线程数小于corePoolSize时,创建线程执行任务。

        2、当线程数大于等于corePoolSize并且workQueue没有满时,放入workQueue中

        3、线程数大于等于corePoolSize并且当workQueue满时,新任务新建线程运行,线程总数要小于maximumPoolSize

        4、当线程总数等于maximumPoolSize并且workQueue满了的时候执行handler的rejectedExecution。也就是拒绝策略。

ThreadPoolExecutor默认有四个拒绝策略:

        1、ThreadPoolExecutor.AbortPolicy()   直接抛出异常RejectedExecutionException

        2、ThreadPoolExecutor.CallerRunsPolicy()    直接调用run方法并且阻塞执行

        3、ThreadPoolExecutor.DiscardPolicy()   直接丢弃后来的任务

        4、ThreadPoolExecutor.DiscardOldestPolicy()  丢弃在队列中队首的任务

当然可以自己继承RejectedExecutionHandler来写拒绝策略.

?
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
         int  corePoolSize =  1 ;
         int  maximumPoolSize =  2 ;
         int  keepAliveTime =  10 ;
//      BlockingQueue<Runnable> workQueue = new LinkedBlockingQueue<Runnable>();
         BlockingQueue<Runnable> workQueue =  new  ArrayBlockingQueue<Runnable>( 5 );
         ThreadFactory threadFactory = Executors.defaultThreadFactory();
         //线程池和队列满了之后的处理方式
         //1.跑出异常
         RejectedExecutionHandler handler =  new  ThreadPoolExecutor.AbortPolicy(); 
         RejectedExecutionHandler handler2 =  new  ThreadPoolExecutor.CallerRunsPolicy();
         RejectedExecutionHandler handler3 =  new  ThreadPoolExecutor.DiscardPolicy();
         RejectedExecutionHandler handler4 =  new  ThreadPoolExecutor.DiscardOldestPolicy();
 
         
         ThreadPoolExecutor threadPoolExecutor =  new  ThreadPoolExecutor(corePoolSize, maximumPoolSize, keepAliveTime, TimeUnit.SECONDS, workQueue, threadFactory, handler2);
         
         
         for  ( int  j =  1 ; j <  15 ; j++) {
             threadPoolExecutor.execute( new  Runnable() {
                 
                 public  void  run() {
                     
                     try  {
                         System.out.println(Thread.currentThread().getName());
                         TimeUnit.SECONDS.sleep( 1 );
                     catch  (InterruptedException e) {
                         e.printStackTrace();
                     }
                     
                     
                 }
             });
         }
         
         System.out.println(threadPoolExecutor);
         
     }


<think>好的,用户问的是JavaThreadPoolExecutor的使用示例。首先我需要回忆一下线程池的基本概念和核心参数ThreadPoolExecutorJava中用来管理线程池的类,主要目的是为了提高线程复用,减少创建和销毁的开销。 接下来,用户可能需要一个具体的代码示例。我应该先介绍构造方法中的各个参数,比如corePoolSize、maximumPoolSize、keepAliveTime、unit、workQueue、threadFactory、handler。然后给出一个简单的例子,创建线程池并提交任务。 然后,我需要考虑用户可能的实际应用场景。比如任务队列的类型选择,比如使用LinkedBlockingQueue还是SynchronousQueue,不同的拒绝策略等。在示例中,可能需要展示如何正确关闭线程池,比如调用shutdown()方法。还要注意线程池的生命周期管理,比如提交任务后如何等待所有任务完成,或者处理异常情况。此外,可能需要提醒用户避免资源泄漏,确保在适当的时候关闭线程池。 用户可能对线程池的工作原理不太清楚,所以在示例中需要简要说明各个参数的作用,比如核心线程数和最大线程数的区别,空闲线程的存活时间,以及任务队列的容量限制。 另外,可能需要提到常见的拒绝策略,比如AbortPolicy、CallerRunsPolicy等,并在示例中展示如何设置自定义的拒绝策略。 最后,根据要求,回答结束后需要提出3-5个相关问题。这些问题应该覆盖参数配置、任务队列选择、拒绝策略、关闭线程池的方法,以及线程池的优点等。确保问题与用户的问题紧密相关,并且能够引导用户深入理解ThreadPoolExecutor的使用。</think>下面是一个简单的 `ThreadPoolExecutor` 使用示例: ```java import java.util.concurrent.*; public class ThreadPoolExample { public static void main(String[] args) { // 核心线程数、最大线程数、空闲线程存活时间、时间单位、任务队列、线程工厂、拒绝策略 ThreadPoolExecutor executor = new ThreadPoolExecutor( 2, // corePoolSize 4, // maximumPoolSize 60, // keepAliveTime TimeUnit.SECONDS, new LinkedBlockingQueue<>(10), // 任务队列容量 Executors.defaultThreadFactory(), // 默认线程工厂 new ThreadPoolExecutor.AbortPolicy() // 拒绝策略 ); // 提交任务 for (int i = 0; i < 15; i++) { final int taskIndex = i; executor.execute(() -> { System.out.println("正在执行任务 " + taskIndex + ",线程:" + Thread.currentThread().getName()); try { Thread.sleep(2000); // 模拟任务耗时 } catch (InterruptedException e) { e.printStackTrace(); } }); } // 关闭线程池(需在任务提交后调用) executor.shutdown(); } } ``` ### 输出说明 - 核心线程数为2,优先启动2个线程处理任务; - 当任务数超过队列容量时,会创建新的线程(最多到4个); - 任务队列容量为10,超过后根据拒绝策略处理(此处抛出异常)。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值