【Java多线程】自定义线程池

本文介绍了线程池的基本概念及其实现方式,包括固定数量的线程池、单线程池和可根据需求调整大小的线程池。此外,还提供了自定义线程池的具体实现代码,并展示了如何在实际应用中提交任务。

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

什么是线程池

在日常的开发中,使用多线程处理一些并发任务的需求经常会见到,为了避免重复的创建和销毁线程,我们可以使用线程池达到线程复用的目的。当需要线程时,从线程池中获取一个空闲的线程;当完成工作时,将线程归还到线程池中。

JDK对线程池的实现

在这里插入图片描述
以上成员均在java.util.concurrent包中。
ThreadPoolExecutor表示一个线程池。

Executor框架提供的方法如下

newFixedThreadPool()

该方法返回一个固定数量的线程池,线程池中的线程数量不变。当有新任务提交,若线程池中有空闲线程,任务会立即执行;若没有空闲线程,会将任务放到队列中,待有空闲线程的时候,再执行。

newSingleThreadExecutor()

该方法返回只有一个线程的线程池,若多余一个任务提交到线程池,任务会被暂存到一个队列中。线程空闲时,从队列中按照先入先出的顺序执行队列中的任务。

newCachedThreadPool()

该方法返回一个可以根据实际情况进行调整的线程池。若线程池中的所有线程都在工作,这时又有新的任务提交,则会创建新的线程进行执行任务。所有线程处理完成任务后,返回线程池进行复用。

核心线程池的内部实现

无论是newFixedThreadPool()、newSingleThreadExecutor()还是newCachedThreadPool(),他们的内部都是通过ThreadPoolExecutor类来实现的。

public ThreadPoolExecutor(int corePoolSize,
                          int maximumPoolSize,
                          long keepAliveTime,
                          TimeUnit unit,
                          BlockingQueue<Runnable> workQueue,
                          ThreadFactory threadFactory,
                          RejectedExecutionHandler handler)
  • corePoolSize:线程池中线程数量。
  • maximumPoolSize:线程池中最大线程数量
  • keepAliveTime:超过corePoolSize的多余线程,在多久时间内会被销毁。
  • unit:keepAliveTime的时间单位。
  • workQueue:任务队列,被提交但是未被执行的任务。
  • threadFactory:线程工厂,用于创建线程。
  • handler:拒绝策略。当任务太多来不及处理时,如何拒绝策略。

自定义一个线程池

public class ThreadPoolConfig {
    /**
     * 核心线程数
     */
    private static final int corePoolSize = 4;
    /**
     * 最大线程数
     */
    private static final int maxPoolSize = 8;
    /**
     * 多余线程最大空闲时间
     */
    private static final int keepAlive = 30;
    /**
     * 线程池缓冲队列
     *  如果不手动指定容量,默认为Integer.MAX_VALUE,也就是无界队列。
     */
    private static final BlockingQueue poolQueue = new LinkedBlockingQueue(64);

    private static volatile ThreadPoolExecutor poolExecutor;

    private ThreadPoolConfig(){}

    public static ThreadPoolExecutor getInstance(){
        if (poolExecutor == null){
            synchronized (ThreadPoolConfig.class){
                if (poolExecutor == null){
                    poolExecutor = new ThreadPoolExecutor(corePoolSize,
                            maxPoolSize,
                            keepAlive,
                            TimeUnit.SECONDS,
                            poolQueue,
                            new ThreadPoolExecutor.DiscardOldestPolicy());
                }
            }
        }
        return poolExecutor;
    }
}

再提供一个util用于向线程池中提交任务

public class ThreadPoolUtil {
    private static ThreadPoolExecutor poolExecutor = ThreadPoolConfig.getInstance();
    public static String submit(Callable callable) throws ExecutionException, InterruptedException {
        Future<String> future = poolExecutor.submit(callable);
        String result = future.get();
        return result;
    }

    public static void execute(Runnable runnable){
        poolExecutor.execute(runnable);
    }

    public static void shutdown(){
        poolExecutor.shutdown();
    }
}

以上两部分代码即完成了线程池的定义,下面写一些代码测试一下

public class TestThreadPool {
    public static void main(String[] args) throws ExecutionException, InterruptedException {

        String re = ThreadPoolUtil.submit(() -> {
            System.out.println("do something...");
            return "success";
        });
        System.out.println(re);

        ThreadPoolUtil.execute(() -> System.out.println("I'm a little thread."));

        ThreadPoolUtil.shutdown();

    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值