在RxJava中,有5种不同的调度器可供选择:
immediate():创建并返回在当前线程上立即执行工作的计划程序
trampoline():创建并返回一个调度程序,该调度程序将当前线程上的工作排队,以便在当前工作完成后执行
newThread():创建并返回一个调度程序,该调度程序为每个工作单元创建一个新线程
计算():创建并返回用于计算工作的计划程序。这可以用于事件循环、处理回调和其他计算工作。不要在此计划程序上执行IO绑定工作。使用调度程序。io()
io():创建并返回用于io绑定工作的计划程序。
该实现由执行器线程池支持,该线程池将根据需要增长。这可用于异步执行阻塞IO。不要在此计划程序上执行计算工作。使用调度程序。计算()
问题:
前3个调度器是非常不言自明的;然而,我对计算和io有点困惑
- 什么是“IO绑定工作”?它是否用于处理流(
java.io)和文件(java.nio.files)?它用于数据库查询吗?它是用于下载文件还是访问RESTAPI - 计算()与新线程()有何不同?是不是所有计算()调用每次都在一个(后台)线程上,而不是在一个新的(后台)线程上
- 为什么在执行IO工作时调用计算()不好
- 为什么在做计算工作时调用io()不好
很好的问题,我认为文档可以做得更详细一些
io()由一个无限的线程池支持,是一种用于非计算密集型任务的东西,这种东西不会给CPU带来太多负载。因此,与文件系统的交互、与不同主机上的数据库或服务的交互就是很好的例子computation()由大小等于可用处理器数量的有界线程池支持。如果您试图在超过可用处理器的范围内并行安排CPU密集型工作(例如使用newThread()),那么您将面临线程创建开销和上下文切换开销,因为线程争夺处理器,这可能会对性能造成巨大影响- 最好将
computation()留给CPU密集型工作,否则您将无法获得良好的CPU利用率 - 调用
io()进行计算工作是不好的,原因如2所述io()是无限的,如果您在io()上并行调度一千个计算任务,那么这一千个任务中的每一个都将有自己的线程,并且都将与CPU竞争,从而产生上下文切换成本