Java 线程池ExecutorService运行原理 和FutureTask 的使用
一.线程池ExecutorService运行原理
ThreadPoolExecutor中有corePoolSize(核心线程)和maximumPoolSize(工作线程),默认核心线程和工作线程数量一致。
1.当线ExecutorService线程池,使用submit,或者execute时
2.先判断运行中的线程是否大于corePoolSize(核心线程)数量
3.如果大于corePoolSize(核心线程)且maximumPoolSize(工作线程)未满则把该线程存着到工作线程等待。
4.如果大于corePoolSize(核心线程)且maximumPoolSize(工作线程)满了则抛出异常(可配置处理策略)。
5.如果小于corePoolSize(核心线程)则把该线程立即运行。
二.代码实现
package com.springboot.demo; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import java.util.concurrent.*; @SpringBootApplication public class DemoApplication { public static void main(String[] args)throws InterruptedException, ExecutionException { SpringApplication.run(DemoApplication.class, args); //定义线程池,ThreadPoolExecutor的方法实现, ExecutorService executorService = Executors.newFixedThreadPool(5); //用 FutureTask 包装线程 可以得到返回值 //isCancelled方法表示任务是否被取消成功,如果在任务正常完成前被取消成功,则返回 true。 //isDone方法表示任务是否已经完成,若任务完成,则返回true; //get()方法用来获取执行结果,这个方法会产生阻塞,会一直等到任务执行完毕才返回; //get(long timeout, TimeUnit unit)用来获取执行结果,如果在指定时间内,还没获取到结果,就直接返回null。 FutureTask<String> futureTaskCallable = new FutureTask<>(new TaskCallable()); executorService.submit(futureTaskCallable); //打印执行结果 System.out.println("执行结果:"+futureTaskCallable.get()); //submit 方法 本质上也是调了execute 仅仅做了一个返回值包装而已。 //Runnable 类 submit execute 都可以执行 executorService.submit(new TaskRunnable()); executorService.execute(new TaskRunnable()); //Callable类 只能 submit executorService.submit(new TaskCallable()); //shutdown()与 shutdownNow() 的区别 executorService.shutdown();//关闭线程池,不允许增加新的线程,但已有线程继续运行至结束。 executorService.shutdownNow();//关系线程池,线程池里的线程,立即停止执行。 } } //实现Runnable 实现 run 方法 class TaskRunnable implements Runnable{ @Override public void run(){ System.out.println(Thread.currentThread().getName() +"##########实现 Runnable 重写 run方法############"); } } //实现Callable call方法 class TaskCallable implements Callable<String>{ @Override public String call(){ System.out.println(Thread.currentThread().getName() +"$$$$$$$$$$$实现Callable call方法$$$$$$$$$$$$$$"); return Thread.currentThread().getName(); } }