线程池基础可以参考 https://www.cnblogs.com/enhance/p/11009997.html
线程池创建方式:
newFixedThreadPool:
使用的构造方式为new ThreadPoolExecutor(var0, var0, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue()),设置了corePoolSize=maxPoolSize,keepAliveTime=0(此时该参数没作用),无界队列,任务可以无限放入,当请求过多时(任务处理速度跟不上任务提交速度造成请求堆积)可能导致占用过多内存或直接导致OOM异常
newSingleThreadExector:
使用的构造方式为new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue(), var0),基本同newFixedThreadPool,但是将线程数设置为了1,单线程,弊端和newFixedThreadPool一致
newCachedThreadPool:
使用的构造方式为new ThreadPoolExecutor(0, 2147483647, 60L, TimeUnit.SECONDS, new SynchronousQueue()),corePoolSize=0,maxPoolSize为很大的数,同步移交队列,也就是说不维护常驻线程(核心线程),每次来请求直接创建新线程来处理任务,也不使用队列缓冲,会自动回收多余线程,由于将maxPoolSize设置成Integer.MAX_VALUE,当请求很多时就可能创建过多的线程,导致资源耗尽OOM
newScheduledThreadPool:
使用的构造方式为new ThreadPoolExecutor(var1, 2147483647, 0L, TimeUnit.NANOSECONDS, new ScheduledThreadPoolExecutor.DelayedWorkQueue()),支持定时周期性执行,注意一下使用的是延迟队列,弊端同newCachedThreadPool一致
项目开发中线程池推荐创建方式
不允许使用Executors创建,而是通过ThreadPoolExecutor创建
Executors创建方式:
ExecutorService service= Executors.newFixedThreadPool(5);
public void test(){
service.execute(()->{...});
}
因为Executors创建 newFixedThreadPool & newSingleThreadExector容易造成任务无限创入LinkedBlockingQueue造成oom;对于newCachedThreadPool&newScheduledThreadPool容易造成线程无限创建造成oom
ThreadpoolExecutor创建方式:
@Configuration public class ThreadConfig { @Bean(value="threadPoolInstance") public ExecutorService createThreadPoolInstance(){
////通过guava类库的ThreadFactoryBuilder来实现线程工厂类并设置线程名称 ThreadFactory threadFactory=new ThreadFactoryBuilder(). setNameFormat("thread-pool-%d").build(); ExecutorService threadPool=new ThreadPoolExecutor( 5, 10, 60L, TimeUnit.SECONDS, new ArrayBlockingQueue<>(100), new ThreadPoolExecutor.AbortPolicy()); return threadPool; } }
@Service public class BusinessThreadPoolService {
//通过name=threadPoolInstance引用线程池实例 @Resource(name="threadPoolInstance") private ExecutorService executorService; public void execute(){ long current=System.currentTimeMillis(); executorService.execute(new Runnable() { @Override public void run() { //business code... } } }); System.out.println(System.currentTimeMillis()-current); }
}
线程池任务提交方式
execute()
execute只接受runnable類型參數,不可以返回执行结果
public void execute(){ long current=System.currentTimeMillis(); executorService.execute(new Runnable() { @Override public void run() { //business code } }); System.out.println(System.currentTimeMillis()-current); }
submit()
接收runnable/callable类型参数,其中callable允许返回执行结果,允许抛出异常
通过executor.submit提交一个callable,返回一个Future,然后通过这个Future的get方法取得返回值
public void submit() throws ExecutionException, InterruptedException {
long current=System.currentTimeMillis();
Future future=executorService.submit(new Callable<String>() {
@Override
public String call() throws Exception{
// business code
return "this is a test";
}
});
System.out.println("callable result:"+future.get());
}
执行结果:
callable result:this is a test
参考文献:
https://blog.csdn.net/qq_40428665/article/details/121651421
https://blog.csdn.net/qq_25806863/article/details/71214033
https://baijiahao.baidu.com/s?id=1701886340868428458&wfr=spider&for=pc