如何优雅的使用线程池?
2019-12-27 本文已影响0人
就这些吗
- 创建ThreadPoolExecutor,切记创建在类的方法之外,这样就不会调用一次方法,创建一个ThreadPoolExecutor,记得使用有界队列、记得把最大线程数设小一点!
private final static ThreadPoolExecutor executor = new ThreadPoolExecutor(10, 30, 2000, TimeUnit.MILLISECONDS,new ArrayBlockingQueue<Runnable>(100));
2.比较反直觉的一点是,线程池是先把任务加进队列,等队列满了之后再创建核心线程。
3.有运行任务自然也有关闭任务,其实无非就是两个方法 shutdown()/shutdownNow()。
但他们有着重要的区别:
shutdown() 执行后停止接受新任务,会把队列的任务执行完毕。
shutdownNow() 也是停止接受新任务,但会中断所有的任务,将线程池状态变为 stop。
两个方法都会中断线程,用户可自行判断是否需要响应中断。
4.execute()只能接受Runnable类型的任务,没有返回值
submit()管是Runnable还是Callable类型的任务都可以接受,有返回值(需要是Callable实现的线程)
submit()中逻辑一定包含了将异步任务抛出的异常捕获,需要用submi().get()进一步抛出异常,submit()没有这个问题。
execute和submit的参考
如果你使用 execute 方法则会打印错误信息,当你使用 submit 方法却没有调用它的get 方法,异常将会被吞没,因为,如果发生了异常,异常是作为返回值返回的。所以需要进行重写submit方法
@Override
public Future<?> submit(Runnable task) {
//return super.submit(task);
return super.submit(wrap(task, clientTrace(), Thread.currentThread().getName()));
}
原文链接:https://blog.csdn.net/qq_38182963/article/details/78976233
5...未完待续