如果无法处理传入请求,是否可以抛出异常?
所以,我有一些固定的线程池:
private val executor: ThreadPoolExecutor = Executors.newFixedThreadPool(4) as ThreadPoolExecutor
而且我不希望请求进入线程队列如果无法处理,我只想抛出异常。
我试图检查activeCount并抛出异常,如果大于最大池大小但它不能正常工作。
private fun checkPoolSize() {
if (executor.activeCount >= 4) {
throw RuntimeException("Request can't be handled. ")
}
}
对此的一个解决方案是使用容量为0的队列和java.util.concurrent.ThreadPoolExecutor.AbortPolicy
作为RejectedExecutionHandler
。
Executors
中的静态方法不会为此展示您想要的完整参数集,因此您需要直接实例化ThreadPoolExecutor
。在您的情况下,您可以使用以下内容:
new ThreadPoolExecutor(4, /* Core pool size */
4, /* Max pool size */
0, TimeUnit.SECONDS, /* Core th. keep-alive */
new MyQueue<Runnable>(0), /* No queueing allowed */
Executors.defaultThreadFactory(), /* default */
new AbortPolicy()) /* throws when all core threads busy */
几点说明:
Executors.newFixedThreadPool(4)
时的默认行为。Executors.defaultThreadFactory()
是默认的线程工厂,与使用Executors.newFixedThreadPool(4)
时相同。MyQueue
是BlockingQueue
的一个实现,它接受0作为容量(即只能是空的。这当然不是队列,但实现这个允许与JDK提供的ThreadPoolExecutor
无缝集成。)。进一步考虑:
通过对线程池的这种微调,请注意吞吐量将受到限制。这里,考虑到提交给线程池的任务的4个线程和平均等待时间L
(以秒为单位),此配置允许的平均吞吐量为4/L
tasks / second。
当有界队列填满时,您可以使用饱和策略。您可以通过调用setRejectedExecutionHandler()
的ThreadPoolExecutor
来设置饱和度策略。开箱即用的实现是AbortPolicy
,CallerRunsPolicy
,DiscardPolicy
和DiscardOldestPolicy
。 AbortPolicy
是默认值,当有界队列填满时会抛出RejectedExecutionException
。您还可以提供自己的自定义实现。