我正在使用ChenduledThreadPoolExecator来安排大量任务在一小时内均匀运行。
将会有数以万计的任务,在需求激增期间,这可能会增长到数十万或数百万。
通常,使用ThreadPoolExecator,我可以将corePoolSize设置为合理的数字,例如10个线程,然后根据需要允许池增长。
但是,为ChenduledThreadPoolExecator留档说:
因为它使用corePoolSize线程和无界队列充当固定大小的池,所以调整最大PoolSize没有有用的效果
这意味着如果我将corePoolSize设置为10,它将被限制在10个线程。如果我将corePoolSize设置为1000,它将立即分配1000个线程,即使它可能永远不会到达那么多活动线程。
有没有一种替代方法可以让我设置一个高的最大线程数,而无需立即分配所有这些线程?
FYI,需要大量活动线程数的原因是线程是I/O绑定的,而不是CPU绑定的。
有没有一个可以让我设置一个高最大线程数的替代方案
是的!
嗯…也许。也许在不久的将来。
Project Loom是几年来为Java的并发设施带来新功能的努力。
虚拟线程promise通常适用于大多数Java实现的应用程序中的大多数任务。有两个警告:(a)虚拟线程对于CPU绑定的任务是相反的,持续计算没有阻塞(没有用户界面交互、没有日志记录、没有磁盘访问、没有网络访问、没有数据库访问等)。一个例子是视频编码;对于这样的工作,使用Java中的传统线程。(b)利用受限资源的任务需要守门或限制。
在你的场景中,我希望你不需要关心设置线程池大小。在常见情况下,虚拟线程会自动处理它。你不需要随着时间的推移分配任务来避免机器过载——同样,虚拟线程在常见情况下会自动管理它。
有关Project Loom的更多信息,请参阅网络上的许多文章,以及与Loom团队成员(包括Ron Pressler和Alan Bateman)的许多会谈和采访。我推荐YouTube频道JEP Café上的多个近期视频。
答案很简单:
我取代了
scheduledThreadPoolExecutor.schedule(task, delay, timeUnit);
与
scheduledThreadPoolExecutor.schedule(()->executorService.submit(task), delay, timeUnit);
其中执行器服务是一个线程池执行器,允许具有不同于maxPoolSize的核心池大小