rxjava 最大线程数 java最大线程数决定因素

admin2024-06-05  13

Java线程池知识总结

为什么会有线程池

  • 创建线程开销大,主要是时间和内存开销。
    Java线程是映射到操作系统用户线程,创建时需要分配栈空间、计数器等。占用空间大小由-Xss控制,默认是1M。
  • 每次手动创建线程难管理。
    机器的CPU和内存资源能支持的线程数是有限的,创建过多的线程会争抢CPU和占用过多内存,造成程序响应慢甚至“假死”。

线程池原理

  • 数据库连接池等池化资源,一般使用流程:获取资源 -> 执行操作 -> 归还资源。
  • 线程池则不同,实现方式是:生产者-消费者模式
    线程池使用方是生产者,生产任务;线程池是消费者,每个Worker线程循环获取任务执行。
    循环获取任务源码参考java.util.concurrent.ThreadPoolExecutor.runWorker(Worker)

核心线程数corePoolSize、最大线程数maximumPoolSize、缓冲队列workQueue、拒绝策略RejectedExecutionHandler怎么起效的?

  1. 先根据核心线程数corePoolSize创建线程,当核心线程都忙还有新任务来时,任务就进入缓冲队列workQueue;
  2. 当缓冲队列满时,再根据最大线程数maximumPoolSize创建新线程(触发创建新线程的那个任务就是这个线程的第一个任务);
  3. 当达到最大线程数还有任务来时,则执行拒绝策略RejectedExecutionHandler。

为什么是上述策略?

线程池的设计目标是重用线程。如果一出现任务堆积就新建线程,可能会导致频繁创建销毁线程,与线程池设计目标相违背。

线程池使用注意事项

  • 给线程指定有意义的名字。
    仿照java.util.concurrent.Executors.DefaultThreadFactory实现自定义ThreadFactory,或者在spring框架下使用org.springframework.scheduling.concurrent.CustomizableThreadFactory。
  • 使用有界队列做缓冲区。
    使用ArrayBlockingQueue或者带capacity的LinkedBlockingDeque,避免OOM;避免使用Executors工厂方法创建线程池。
  • 代码捕获所有异常。
    线程池执行任务时遇到RuntimeException不会有任何信息,遇到问题不方便排查。
run(){
		try{
			//do job
		}catch(Throwable e){
			//自定义处理
		}
	}

线程池不是银弹

我们不能仅仅因为程序慢,就使用线程池异步执行,重要的还是程序的执行效率。

更多参考

美团这篇文章图文并茂,深入讲解线程池实现原理及动态线程池方案。Java线程池实现原理及其在美团业务中的实践

一种动态线程池方案实现。yinjihuan的动态线程池方案实现


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明原文出处。如若内容造成侵权/违法违规/事实不符,请联系SD编程学习网:675289112@qq.com进行投诉反馈,一经查实,立即删除!