• 【Java线程池ThreadPool(创建线程的第三种方式)】


    CSDN话题挑战赛第2期
    参赛话题:一起学Java

    线程池ThreadPool(创建线程的第三种方式)

    1、线程池的作用

    主要用于创建和管理若干个线程的一种容器,当我们需要执行任务时,可以从池中取出

    线程来执行,当执行完任务后,将线程返回到池中,避免频繁的去创建和销毁线程,从而

    节省空间,提升系统性能

    2、自定义线程池

    ThreadPoolExecutor pool=

    new ThreadPoolExecutor(

    核心线程数,

    最大线程数,

    超时(空闲,活跃)时间,

    超时的时间单位,

    任务队列,

    线程工厂,

    拒绝策略);

    拒绝策略类型:

    * 1》AbortPolicy:拒绝执行新的任务,并抛出异常

    * 2》CallerRunsPolicy:如果线程池没有关闭,不使用线程池中的线程

    * 也不会加入到任务队列,而是让当前线程直接调用run()方法来执行任务,

    * 如果线程池已关闭,则直接丢弃掉该任务不执行

    * 3》DiscardOldestPolicy: 如果线程池没有关闭,将任务队列中存放最久的任务

    * (队首元素)移除掉,并将新的任务加入到任务队列中,如果线程池已经关闭

    * 则直接丢弃掉该任务不执行

    * 4》DiscardPolicy:拒绝执行任务,但是不会抛异常

    3、jdk自带线程

    1》单线程线程池

    ExecutorService es=Executors.newSingleThreadExecutor()

    只有一个核心线程,不允许创建非核心线程;

    等上一个任务执行完了,才能执行下一个任务

    2》固定数量线程池

    ExecutorService es=Executors.newFixedThreadPool(int n);

    传入的参数既是核心线程又是最大线程,

    也就是不允许创建非核心线程

    3》可缓存线程池

    ExecutorService es=Executors.newCachedThreadPool();

    没有核心线程,所有线程均为非核心线程

    有多少任务就会创建多少个线程

    线程最大数量为integer.max_value,

    所有非核心线程空闲时间超过60S就会被回收

    4》周期性线程池

    ExecutorService es=Executors.newScheduledThreadPool(int n);

    自己指定核心线程数

    线程最大数量为integer.max_value

    超时时间为0

    任务队列为延迟队列

    4、线程池的常用方法

    1》execute(Runnable r)

    将任务对象交给线程池,线程池会自动取出空闲线程来执行任务,

    没有空闲线程就将任务加入到任务队列中,队列满了就触发拒绝策略

    2》shutdown()

    安全关闭线程池

    只有等到线程池中所有线程都执行完任务后才会关闭

    如果还有未执行完任务,当前方法会阻塞

    3》shutdownNow();

    立即关闭线程

    无论线程池中是否还有未执行完的额任务,都会立即关闭线程池

    会导致线程池还有未执行完的任务,返回这些未执行的线程

    周期性线程中的主要方法

    1》schedule(Runnable r,long delay, TimeUnit unit)

    延迟指定时间后来执行这个r任务

    2>scheduleAtFixedRate(Runnable command,long initialDelay,long period,TimeUnit unit);

    每间隔period指定的时间后来执行一次任务

    如果一个任务的执行时间超过了间隔时间,

    那么在一个任务执行完成红立即执行下一个任务,

    如果没有超过,那么就在指定间隔时间后执行下一个任务

    3》scheduleWithFixedDelay(Runnable command,long initialDelay,long delay,TimeUnit unit);

    执行周期性任务

    在一个任务执行完成后,再间隔设置的时间后,

    再来执行下一个任务

    1. import java.util.Date;
    2. import java.util.concurrent.ArrayBlockingQueue;
    3. import java.util.concurrent.BlockingQueue;
    4. import java.util.concurrent.ExecutorService;
    5. import java.util.concurrent.Executors;
    6. import java.util.concurrent.RejectedExecutionHandler;
    7. import java.util.concurrent.ScheduledExecutorService;
    8. import java.util.concurrent.ThreadFactory;
    9. import java.util.concurrent.ThreadPoolExecutor;
    10. import java.util.concurrent.ThreadPoolExecutor.AbortPolicy;
    11. import java.util.concurrent.TimeUnit;
    12. /*
    13. * 线程池
    14. */
    15. public class ThreadDemo16 {
    16. public static void main(String[] args) {
    17. //自定义线程池
    18. /**
    19. * 参数解释:
    20. * 1、corePoolSize:核心线程数
    21. * 线程池创建出来时就需要创建的线程数,线程池中需要保证最小数量线程
    22. * 2、maximumPoolSize:最大线程数
    23. * 线程池中允许存在的最大线程数量
    24. * 3、keepAliveTime:超时(空闲,活跃)时间
    25. * 非核心线程在指定时间内没有接收到新的任务,就会被销毁,
    26. * 如果调用了allowCoreThreadTimeOut()方法并且参数为true,
    27. * 那么超过指定时间后,核心线程也会被销毁
    28. * 4、TimeUnit:keepAliveTime超时的时间单位
    29. * 5、workQueue:任务队列
    30. * 需要线程池中的线程执行任务所存放的队列
    31. * 6、threadFactory:线程工厂
    32. * 负责创建线程池中的线程
    33. * 7、RejectedExecutionHandler:拒绝策略
    34. * 当线程池中所有线程都在执行任务,并且任务队列也是满负荷的情况下
    35. * 又有新的任务需要线程池来执行,就会触发拒绝策略
    36. *
    37. * 拒绝策略类型:
    38. * 1》AbortPolicy:拒绝执行新的任务,并抛出异常
    39. * 2》CallerRunsPolicy:如果线程池没有关闭,不使用线程池中的线程
    40. * 也不会加入到任务队列,而是让当前线程直接调用run()方法来执行任务,
    41. * 如果线程池已关闭,则直接丢弃掉该任务不执行
    42. * 3》DiscardOldestPolicy: 如果线程池没有关闭,将任务队列中存放最久的任务
    43. * (队首元素)移除掉,并将新的任务加入到任务队列中,如果线程池已经关闭
    44. * 则直接丢弃掉该任务不执行
    45. * 4》DiscardPolicy:拒绝执行任务,但是不会抛异常
    46. */
    47. // ThreadPoolExecutor pool=
    48. // new ThreadPoolExecutor(
    49. // 3,
    50. // 3,
    51. // 10,
    52. // TimeUnit.SECONDS,
    53. // new ArrayBlockingQueue(5),
    54. // new ThreadFactory() {
    55. //
    56. // @Override
    57. // public Thread newThread(Runnable r) {
    58. // return new Thread(r);
    59. // }
    60. // },
    61. //
    62. // new AbortPolicy());
    63. //
    64. // //创建任务对象,并交给线程池执行
    65. // //线程池会自动取出空闲线程来执行该任务
    66. // pool.execute(new ThreadTask("A"));
    67. // pool.execute(new ThreadTask("B"));
    68. // pool.execute(new ThreadTask("C"));
    69. // pool.execute(new ThreadTask("D"));
    70. // pool.execute(new ThreadTask("E"));
    71. // pool.execute(new ThreadTask("F"));
    72. // pool.execute(new ThreadTask("G"));
    73. System.out.println("_____________________________________________");
    74. //系统提供的线程池
    75. /**
    76. * 1、创建单个线程的线程池
    77. * 只有一个核心线程,不允许创建非核心线程;
    78. * 等上一个任务执行完了,才能执行下一个任务
    79. *
    80. */
    81. // ExecutorService es=
    82. // Executors.newSingleThreadExecutor();
    83. /**
    84. * 2、创建固定的数量线程的线程池
    85. * 传入的参数既是核心线程又是最大线程,
    86. * 也就是不允许创建非核心线程
    87. */
    88. // es=
    89. // Executors.newFixedThreadPool(5);
    90. /**
    91. * 3、创建可缓存线程池
    92. * 没有核心线程,所有线程均为非核心线程
    93. * 有多少任务就会创建多少个线程
    94. * 线程最大数量为integer.max_value,
    95. * 所有非核心线程空闲时间超过60S就会被回收
    96. */
    97. //
    98. // es=
    99. // Executors.newCachedThreadPool();
    100. //
    101. // es.execute(new ThreadTask("A"));
    102. // es.execute(new ThreadTask("B"));
    103. // es.execute(new ThreadTask("C"));
    104. // es.execute(new ThreadTask("D"));
    105. // es.execute(new ThreadTask("E"));
    106. // es.execute(new ThreadTask("F"));
    107. /**
    108. * 4、周期性线程池
    109. * 自己指定核心线程数
    110. * 线程最大数量为integer.max_value
    111. * 超时时间为0
    112. * 任务队列为延迟队列
    113. */
    114. ScheduledExecutorService es=
    115. Executors.newScheduledThreadPool(3);
    116. /**
    117. * 指定延迟多长时间之后来执行任务
    118. *
    119. */
    120. // es.schedule(new Runnable() {
    121. //
    122. // @Override
    123. // public void run() {
    124. // System.out.println(new Date());
    125. // }
    126. // }, 5, TimeUnit.SECONDS);
    127. /**
    128. * 2、执行周期性任务
    129. * 参数解释
    130. * 1》周期执行的任务
    131. * 2》第一次执行任务的的延迟时间
    132. * 3》两次任务执行时间的间隔时间
    133. * 4》时间单位
    134. *
    135. * 如果一个任务的执行时间超过了间隔时间,
    136. * 那么在一个任务执行完成红立即执行下一个任务,
    137. * 如果没有超过,那么就在指定间隔时间后执行下一个任务
    138. */
    139. System.out.println(new Date());
    140. es.scheduleAtFixedRate(new Runnable() {
    141. @Override
    142. public void run() {
    143. System.out.println(new Date());
    144. }
    145. }, 3, 1, TimeUnit.SECONDS);
    146. /**
    147. * 3、执行周期性任务
    148. * 在一个任务执行完成后,再间隔设置的时间后,
    149. * 再来执行下一个任务
    150. */
    151. // System.out.println(new Date());
    152. // es.scheduleWithFixedDelay(new Runnable() {
    153. //
    154. // @Override
    155. // public void run() {
    156. // try {
    157. // Thread.sleep(1000);
    158. // } catch (InterruptedException e) {
    159. // e.printStackTrace();
    160. // }
    161. // System.out.println(new Date());
    162. // }
    163. // }, 3, 1, TimeUnit.SECONDS);
    164. //关闭线程池
    165. /*
    166. * 安全关闭线程池
    167. * 只有等到线程池中所有线程都执行完任务后才会关闭
    168. * 如果还有未执行完任务,当前方法会阻塞
    169. */
    170. // es.shutdown();
    171. /*
    172. * 立即关闭线程
    173. * 无论线程池中是否还有未执行完的额任务,都会立即关闭线程池
    174. * 会导致线程池还有未执行完的任务,返回这些未执行的线程
    175. */
    176. // pool.shutdownNow();
    177. }
    178. }
    179. //线程池需要执行的任务
    180. class ThreadTask implements Runnable{
    181. private String name;
    182. public ThreadTask(String name) {
    183. this.name=name;
    184. }
    185. @Override
    186. public void run() {
    187. System.out.println(
    188. Thread.currentThread().getName()+"线程正在执行"+name+"任务");
    189. }
    190. @Override
    191. public String toString() {
    192. return "名称为"+name+"任务";
    193. }
    194. }

  • 相关阅读:
    ThreadLocal底层源码分析
    SpringBoot-42-注册Web原生组件
    有用FPGA开发长光辰芯HR400BSI探测器的吗?有偿请教技术问题
    视频怎么添加水印?快来收好这些方法
    sqlserver 联表查询、子查询、窗口函数、聚合函数等概念与例子
    【产品运营】你真的懂B端大客户吗?来试试这8个棘手的需求问题
    这款信创FTP软件,可实现安全稳定的文件传输
    vue3 电子签名实现
    AI做题水平已超过CS博士?
    谷粒商城项目总结(一)-基础篇
  • 原文地址:https://blog.csdn.net/m0_72254454/article/details/126941236