Java ThreadPoolExecutor 创建新线程
在Java编程中,线程是一种轻量级的执行单元,可以并行执行代码。而线程池就是管理和复用线程的工具,通过线程池可以提高程序的性能和效率。Java提供了ThreadPoolExecutor类来实现线程池的功能。
ThreadPoolExecutor 概述
ThreadPoolExecutor是Java提供的一个灵活的线程池实现,它可以根据需要创建新线程,并在完成任务后将线程保留一段时间以备重用。这样可以避免频繁创建和销毁线程的开销,提高系统的性能。
ThreadPoolExecutor类有多个构造方法可以使用,最常用的构造方法有以下几个参数:
- corePoolSize:线程池中保持的最小线程数
- maximumPoolSize:线程池中允许的最大线程数
- keepAliveTime:线程空闲时的存活时间
- unit:keepAliveTime的时间单位
- workQueue:用于保存等待执行的任务的阻塞队列
- threadFactory:用于创建新线程的工厂
- handler:拒绝策略,当线程池无法接受新任务时的处理方式
ThreadPoolExecutor 示例代码
下面是一个简单的示例代码,演示了如何使用ThreadPoolExecutor创建一个线程池,并提交任务给线程池执行。
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class ThreadPoolExample {
public static void main(String[] args) {
// 创建一个固定大小的线程池,最多同时执行两个任务
ExecutorService executor = Executors.newFixedThreadPool(2);
// 提交任务给线程池执行
executor.submit(() -> {
System.out.println("Task 1 is running");
});
executor.submit(() -> {
System.out.println("Task 2 is running");
});
executor.submit(() -> {
System.out.println("Task 3 is running");
});
// 关闭线程池
executor.shutdown();
}
}
在上面的示例中,我们首先使用Executors工厂类的newFixedThreadPool方法创建了一个固定大小的线程池,最多同时执行两个任务。然后通过executor.submit方法提交了三个任务给线程池执行,最后调用executor.shutdown方法关闭线程池。
ThreadPoolExecutor 拒绝策略
当线程池无法接受新任务时,可以通过设置拒绝策略来处理这种情况。ThreadPoolExecutor提供了几种内置的拒绝策略:
- AbortPolicy:默认的拒绝策略,直接抛出RejectedExecutionException异常
- CallerRunsPolicy:让提交任务的线程来执行任务
- DiscardPolicy:直接丢弃新任务
- DiscardOldestPolicy:丢弃队列中等待时间最长的任务,然后执行新任务
自定义线程池
除了使用Executors工厂类提供的线程池之外,我们也可以通过ThreadPoolExecutor类自定义线程池。下面是一个示例代码:
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
public class CustomThreadPoolExample {
public static void main(String[] args) {
// 创建一个自定义的线程池
ThreadPoolExecutor executor = new ThreadPoolExecutor(
2, 4, 10, TimeUnit.SECONDS, new ArrayBlockingQueue<>(2),
r -> new Thread(r, "custom-thread-" + r.hashCode()),
new ThreadPoolExecutor.AbortPolicy());
// 提交任务给线程池执行
executor.submit(() -> {
System.out.println("Task 1 is running on " + Thread.currentThread().getName());
});
executor.submit(() -> {
System.out.println("Task 2 is running on " + Thread.currentThread().getName());
});
executor.submit(() -> {
System.out.println("Task 3 is running on " + Thread.currentThread().getName());
});
executor.submit(() -> {
System.out.println("Task 4 is running on " + Thread.currentThread().getName());
});
executor.submit(() -> {
System.out.println("Task 5 is running on " + Thread.currentThread().getName());
});
// 关闭线程池
executor.shutdown();
}
}
在上面的示例中,我们使用ThreadPoolExecutor类自定义了一个线程池,设置了核心线程数为2,最大线程数为4,工