Java多线程
线程的创建方式:
1. 继承Thread类创建线程;
2. 实现Runnable接口创建线程;
3. 使用Callable和Future创建线程;
4. 使用线程池创建线程。
线程的状态转换:
1. 新建状态(new);
2. 就绪状态(Runnable);
3. 运行状态(Running);
4. 阻塞状态(Blocked);
5. 死亡状态(Dead)。
其中阻塞状态(Blocked)分为三种情况:
1. 调用线程的wait()方法,让线程等待某工作完成,进入等待阻塞;
2. 获取同步锁synchronized失败,进入同步阻塞;
3. 其他阻塞,调用线程的sleep()或者join()或者发出I/O请求时,会进入其他阻塞。

线程池:
线程池就是把多个线程事先存储到一个池子中,使用时无需new线程,而是直接到池子中获取线程即可,节省了创建线程的时间,提高效率。
在java.util.concurrent.Executors类中提供了生成线程池的静态方法(不推荐直接使用,推荐使用线程池构造方法创建线程池,便于根据具体业务场景设置线程数和队列大小),如:
ExecutorService newCachedThreadPool = Executors.newCachedThreadPool(); ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(4); ScheduledExecutorService newScheduledThreadPool = Executors.newScheduledThreadPool(4); ExecutorService newSingleThreadExecutor = Executors.newSingleThreadExecutor();
调用他们的execute方法即可。
1. newCachedThreadPool 可缓存线程池
工作线程的创建数量几乎没有限制(最大数目为Interger. MAX_VALUE,基本用不完),可以灵活在线程池中添加线程,如果线程池中线程数量超出任务需求,可回收空闲线程,否则新建线程。
2. newFixedThreadPool 指定工作线程数量的线程池
每当提交一个任务就创建一个工作线程,到达最大线程数时,将提交的任务放入工作队列中。优点:提高程序效率,节省创建线程的开销。缺点:线程池空闲时不会释放工作线程,会占用一定的系统资源。
3. newScheduleThreadPool 支持定时和周期性任务的线程池
固定核心线程数,核心线程会一直存活来处理任务,支持定时任务和周期性任务,任务并发执行,互不干扰。优点:线程数固定,避免无限制创建线程,统一管理线程。但核心线程固定,不灵活,工作任务激增时不能通过增加线程数来解决问题。
4. newSingleThreadExecutor 单线程化的Executor
只创建一个工作线程来执行任务,保证所有任务按照指定顺序(FIFO, LIFO)执行,如果该线程异常结束,会有另一个线程取代它,保证任务执行。
ThreadPoolExecutor对象的七个参数:
corePoolSize:核心线程数,
maximumPoolSize:最大线程数
keepAliveTime 存活时间
unit: 存活时间keepAliveTime 的单位
workQueue 工作队列
threadFactory 线程工厂
RejectedExecutionHandler 拒绝策略。
拒绝策略:
AbortPolicy直接抛出异常,默认
CallerRunsPolicy 由调用者所在的线程来执行任务
DiscardOldestPolicy 丢弃阻塞队列中靠前任务,并执行当前任务
DiscardPolicy 直接丢弃任务
可通过RejectedExecutionHandler 接口,自定义拒绝策略,例如使用持久化存储任务。
线程池工作流程:

浙公网安备 33010602011771号