在 Java 中,创建线程池的方式主要有以下几种:
1. 使用 Executors
工厂类
Executors
是 Java 提供的一个工具类,提供了多种创建线程池的静态工厂方法。以下是常见的几种线程池:
(1)固定大小线程池(FixedThreadPool)
- 特点:线程池中的线程数量固定。
- 适用场景:适用于负载较重的服务器,需要限制线程数量以避免资源耗尽。
(2)单线程线程池(SingleThreadExecutor)
- 特点:线程池中只有一个线程。
- 适用场景:适用于需要保证任务顺序执行的场景。
(3)缓存线程池(CachedThreadPool)
- 特点:线程池中的线程数量不固定,根据需要创建新线程,空闲线程会被回收。
- 适用场景:适用于执行大量短期异步任务。
(4)定时任务线程池(ScheduledThreadPool)
- 特点:支持定时及周期性任务执行。
- 适用场景:适用于需要定时执行任务的场景。
(5)单线程定时任务线程池(SingleThreadScheduledExecutor)
- 特点:只有一个线程的定时任务线程池。
- 适用场景:适用于需要单线程定时执行任务的场景。
2. 使用 ThreadPoolExecutor
构造函数
ThreadPoolExecutor
是 Java 线程池的核心实现类,通过其构造函数可以更灵活地创建线程池。
构造函数参数:
- corePoolSize:核心线程数。
- maximumPoolSize:最大线程数。
- keepAliveTime:空闲线程的存活时间。
- unit:存活时间的单位。
- workQueue:任务队列。
- threadFactory:线程工厂。
- handler:拒绝策略。
示例:
import java.util.concurrent.*;
public class ThreadPoolExecutorExample {
public static void main(String[] args) {
ThreadPoolExecutor executor = new ThreadPoolExecutor(
2, // 核心线程数
5, // 最大线程数
60, // 空闲线程存活时间
TimeUnit.SECONDS, // 时间单位
new LinkedBlockingQueue<>(10), // 任务队列
Executors.defaultThreadFactory(), // 线程工厂
new ThreadPoolExecutor.AbortPolicy() // 拒绝策略
);
executor.execute(() -> System.out.println("任务执行"));
executor.shutdown();
}
}
3. 使用 ForkJoinPool
ForkJoinPool
是 Java 7 引入的线程池,适用于分治任务的并行执行。
特点:
- 支持工作窃取(Work-Stealing)算法,提高并行任务的执行效率。
- 适用于递归任务或分治任务。
示例:
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.RecursiveTask;
public class ForkJoinPoolExample {
public static void main(String[] args) {
ForkJoinPool forkJoinPool = new ForkJoinPool();
int result = forkJoinPool.invoke(new FibonacciTask(10));
System.out.println("Fibonacci 结果: " + result);
}
}
class FibonacciTask extends RecursiveTask<Integer> {
private final int n;
FibonacciTask(int n) {
this.n = n;
}
@Override
protected Integer compute() {
if (n <= 1) {
return n;
}
FibonacciTask task1 = new FibonacciTask(n - 1);
task1.fork();
FibonacciTask task2 = new FibonacciTask(n - 2);
return task2.compute() + task1.join();
}
}
4. 自定义线程池
通过继承 ThreadPoolExecutor
或实现 ExecutorService
接口,可以创建自定义的线程池。
示例:
import java.util.concurrent.*;
public class CustomThreadPool extends ThreadPoolExecutor {
public CustomThreadPool(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue) {
super(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue);
}
@Override
protected void beforeExecute(Thread t, Runnable r) {
System.out.println("任务执行前: " + r);
}
@Override
protected void afterExecute(Runnable r, Throwable t) {
System.out.println("任务执行后: " + r);
}
public static void main(String[] args) {
CustomThreadPool executor = new CustomThreadPool(2, 5, 60, TimeUnit.SECONDS, new LinkedBlockingQueue<>());
executor.execute(() -> System.out.println("任务执行"));
executor.shutdown();
}
}
5. 总结
创建方式 | 特点 | 适用场景 |
---|---|---|
Executors.newFixedThreadPool | 固定线程数 | 负载较重的服务器 |
Executors.newSingleThreadExecutor | 单线程 | 需要顺序执行的任务 |
Executors.newCachedThreadPool | 线程数动态调整 | 大量短期异步任务 |
Executors.newScheduledThreadPool | 支持定时任务 | 定时任务 |
ThreadPoolExecutor | 灵活配置线程池参数 | 需要精细控制的场景 |
ForkJoinPool | 支持分治任务和工作窃取 | 递归任务或分治任务 |
自定义线程池 | 完全自定义线程池行为 | 特殊需求的场景 |
根据具体需求选择合适的线程池创建方式,可以提高程序的性能和可维护性。
THE END
暂无评论内容