目录
一、线程状态:
- 新建状态(new):创建线程对象之后;
- 就绪状态(Runnable):调用start()方法之后;
- 运行状态(Running):调用run(),即处于就绪状态的线程获取cpu资源之后;
- 阻塞状态(Blocked):运行中的线程由于某种原因放弃cpu资源,停止执行;
- 等待阻塞:运行中的线程执行wait()方法,进入等待;
- 同步阻塞:运行中的线程申请同步锁中的资源失败进入阻塞;
- 其他阻塞:sleep()、join()、发出io请求时线程会进入阻塞;
- 死亡状态(Dead):线程执行完成或因异常退出线程。
二、多线程实现方式
- 继承Thread,重写run()
Thread t = new MyThread();
t.start();
- 实现Runnable,实现run()方法
// 创建一个Runnable实现类的对象
Runnable myRunnable = new MyRunnable();
Thread thread1 = new Thread(myRunnable);
thread1.start();
- 使用Callable和Future,实现call()方法
// 创建MyCallable对象
Callable<Integer> myCallable = new MyCallable();
FutureTask<Integer> ft = new FutureTask<Integer>(myCallable);
Thread t = new Thread(ft);
t.start();
//获取线程返回结果
int a = ft.get();
- 线程池
三、线程池
- Executor:线程池最上层接口,提供execute(Runnable run)执行异步任务;
- ExecutorService:线程池服务接口,提供一系列服务方法;
public interface ExecutorService extends Executor {
// 执行完现有任务,停止接受新任务
void shutdown();
// 现有任务停止(不一定成功),忽略等待任务,停止接受新任务,返回未执行完的任务列表
List<Runnable> shutdownNow();
// 只要执行过shutdown()返回 true
boolean isShutdown();
// 所有任务都已完成,则返回 true
boolean isTerminated();
// 阻塞当前线程,直到所有任务(正在执行和等待)完成执行、超时、异常
boolean awaitTermination(long timeout, TimeUnit unit) throws InterruptedException;
// 返回call()方法返回值
<T> Future<T> submit(Callable<T> task);
// 执行Runnable的run()方法之后,Future.get()返回传入的result
<T> Future<T> submit(Runnable task, T result);
// 执行Runnable的run()方法之后,Future.get()返回null
Future<?> submit(Runnable task);
// 执行给定的任务,当所有任务完成时,返回保持任务状态和结果的 Future 列表
<T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks)
throws InterruptedException;
// 执行给定的任务,当所有任务完成或超时期满时,返回保持任务状态和结果的 Future 列表
<T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks,
long timeout, TimeUnit unit)
throws InterruptedException;
// 执行给定的任务,如果某个任务已成功完成(也就是未抛出异常),则返回其结果
<T> T invokeAny(Collection<? extends Callable<T>> tasks)
throws InterruptedException, ExecutionException;
// 执行给定的任务,如果在给定的超时期满前某个任务已成功完成(也就是未抛出异常),则返回其结果
<T> T invokeAny(Collection<? extends Callable<T>> tasks,
long timeout, TimeUnit unit)
throws InterruptedException, ExecutionException, TimeoutException;
}
- AbstractExecutorService:抽象类,实现了除shutdown()、shutdownNow()、execute()、isShutdown()、isTerminated()以外的方法;其中submit(Runnable task)内部将task转换为FutureTask对象并调用execute();
- ThreadPoolExecutor:线程池实现类
- corePoolSize:线程池大小,提交一个任务,当线程池大小小于corePoolSize时新建一个线程;
- maximumPoolSize:最大线程池大小,当任务队列满了,且已创建线程数小于maximumPoolSize时,会创建新线程执行任务,任务执行完会回收线程至线程池大小,对于无界队列该参数无效;
- keepAliveTime:当线程池大于corePoolSize,且线程空闲时间超过keepAliveTime,回收线程至corePoolSize大小;
- 判断线程超时方式:在 keepAliveTime 的时间内 poll 不到任务则任务超时;
- unit:存活时间单位NANOSECONDS(纳秒),MICROSECONDS(微妙),MILLISECONDS(毫秒),SECONDS(秒),MINUTES(分),HOURS(小时),DAYS(天);
- workQueue:任务队列
- SynchronousQueue:直接提交,即该队列没有大小(容量为0),只有把当前任务提交给线程才能新增;(此队列可防止具有内部依赖的任务执行时出现锁)
- LinkedBlockingQueue:无界队列,队列无大小,可以无限添加任务;(防止任务丢失)
- ArrayBlockingQueue:有界队列,固定大小,超过大小无法添加;(防止资源耗尽,JDK不推荐)
corePoolSize、maximumPollSize、workQueue关系:新增一个任务
- 如果线程池大小 < corePoolSize,新增线程;
- 如果线程池大小 >= corePoolSize,将任务加入任务队列;
- 如果无法加入队列(队列类型或队列大小不支持),新增线程至maximumPoolSize大小;
- 如果线程池大小 >= maximumPoolSize大小,执行拒绝策略。
- threadFactory:线程工厂,用于创建新线程,同一工厂创建的线程属于同一ThreadGroup;
- handler:拒绝策略(当线程池和队列都满时)
- ThreadPoolExecutor.AbortPoilcy:直接抛出异常;
- ThreadPoolExecutor.CallerRunsPoilcy:调用者所在线程执行该任务,可减缓提交任务的速度;
- ThreadPoolExecutor.DiscardPoilcy:删除无法执行的任务;
- ThreadPoolExecutor.DiscardOldestPoilcy:删除任务队列头部的任务。
- Executors工厂方式默认实现了四种创建线程池的方式
- Executors.newCachedThreadPool() 提供了无界线程池,可以进行自动线程回收;
public static ExecutorService newCachedThreadPool() { return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueue<Runnable>()); }
- Executors.newFixedThreadPool(int) 提供了固定大小线程池,内部使用无界队列;
public static ExecutorService newFixedThreadPool(int nThreads) { return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>()); }
- Executors.newScheduledThreadPool(int) 提供了固定大小线程池,支持定时及周期性任务执行;
- DelayedWorkQueue:一个无界队列,它能按一定的顺序对工作队列中的元素进行排列。
public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) { return new ScheduledThreadPoolExecutor(corePoolSize); } public ScheduledThreadPoolExecutor(int corePoolSize) { super(corePoolSize, Integer.MAX_VALUE, 0, NANOSECONDS, new DelayedWorkQueue()); }
- DelayedWorkQueue:一个无界队列,它能按一定的顺序对工作队列中的元素进行排列。
- Executors.newSingleThreadExecutor() 提供了单个后台线程。
public static ScheduledExecutorService newSingleThreadScheduledExecutor() { return new DelegatedScheduledExecutorService (new ScheduledThreadPoolExecutor(1)); }
- Executors.newFixedThreadPool(int) 提供了固定大小线程池,内部使用无界队列;
public static ScheduledExecutorService newSingleThreadScheduledExecutor() { return new DelegatedScheduledExecutorService (new ScheduledThreadPoolExecutor(1)); }
- Executors.newCachedThreadPool() 提供了无界线程池,可以进行自动线程回收;
线程池选择:不推荐使用Executors,使用ThreadPoolExecutor更明确运行规则。
- 任务类型
- CPU密集型:需要做很多判断、计算等CPU动作的任务;cpu密集型任务对cpu需求较大,应配置尽可能小的线程池大小:n+1;
- IO密集型:需要做很多写硬盘、读硬盘的操作;io密集型任务对cpu需求不大,因为io操作不占用cpu,可以配置多个线程池:2n+1。