ThreadPoolExecutor策略

Joe*_*e K 13 java concurrency multithreading executor blockingqueue

我正在尝试使用ThreadPoolExecutor来安排任务,但遇到了一些问题.这是它陈述的行为:

  1. 如果运行的corePoolSize线程少于corePoolSize,则Executor总是更喜欢添加新线程而不是排队.
  2. 如果corePoolSize或更多线程正在运行,则Executor总是更喜欢排队请求而不是添加新线程.
  3. 如果请求无法排队,则会创建一个新线程,除非它超过maximumPoolSize,在这种情况下,该任务将被拒绝.

我想要的行为是这样的:

  1. 与上述相同
  2. 如果正在运行corePoolSize以上但不到maximumPoolSize线程,则更喜欢在排队时添加新线程,并在添加新线程时使用空闲线程.
  3. 与上述相同

基本上我不希望任何任务被拒绝; 我希望他们在无限队列中排队.但我确实想拥有maximumPoolSize线程.如果我使用无界队列,它在击中coreSize后就不会生成线程.如果我使用有界队列,它会拒绝任务.有没有办法解决?

我现在正在考虑的是在SynchronousQueue上运行ThreadPoolExecutor,但不直接向它提供任务 - 而是将它们提供给单独的无界LinkedBlockingQueue.然后另一个线程从LinkedBlockingQueue进入Executor,如果一个被拒绝,它只是再次尝试,直到它被拒绝.这看起来像是一种痛苦而且有点像黑客 - 有更清洁的方法吗?

Hol*_*tte 1

您的用例很常见,完全合法,但不幸的是比人们想象的要困难。有关背景信息,您可以阅读此讨论并在此处找到解决方案的指针(也在线程中提到)。谢伊的解决方案效果很好。

一般来说,我会对无界队列有点警惕;通常最好有明确的传入流量控制,可以优雅地降级并调节当前/剩余工作的比率,以免压垮生产者或消费者。