[英]Java ExecutorService, setting an overall fixed rate for all work in a queue
给出以下代码:
ScheduledExecutorService es = new ScheduledThreadPoolExecutor(100);
es.scheduleAtFixedRate(() -> {
System.out.println("Do work with a fixed rate! ");
}, 0, 1000, TimeUnit.MILLISECONDS);
int i = 0;
while ( i < 100 ) {
es.scheduleAtFixedRate(() -> {
System.out.println("Do more work with a fixed rate! Doesn't really work! We will end up with 100 'workers', each running with a fixed rate! ");
}, 0, 1000, TimeUnit.MILLISECONDS);
i++;
}
这将创建一个SchedueledThreadPoolExecutor 。
在while循环中,我们正在模拟其他想要向队列添加更多工作的人,但这显然行不通。
我猜想,一个人需要实现某种ThreadPoolExecutor,它使用某种队列,可能是延迟队列。
这个想法是创建执行程序,然后以固定的速率执行任务。 如果任务完成得太快,则需要等待完成的线程才能完成更多工作。
如果一个进程完成得太慢,则全局时间应允许线程池中的其他线程完成更多工作。
http://docs.oracle.com/javase/7/docs/api/java/util/AbstractQueue.html
http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/DelayQueue.html
但是我希望这已经完成,因为这应该是很常见的问题。
有人对此有很好的解决方案吗?
目前尚不清楚您要做什么,但是我想您想要一种起搏器或节流阀,以确保以一定的速率执行任务(想想在办公楼和其他建筑物入口处发现的旋转门,门的速度决定了每个时间单位可进入(或离开)建筑物的人数以及每个入口(或出口)之间的时间差。
ScheduledExecutorServcice 不能解决该问题。 相反,首先要研究“ 漏桶”算法 。
ScheduledThreadPoolExecutor
维护任务队列,这些任务由任务的下一个计划执行顺序排序。 这些任务(您提供的Runnable
实例)完全独立于将执行它们的线程。 换句话说,线程不仅获取任务,执行任务,然后进入睡眠状态等待任务的下一次执行。
而是,线程轮询队列,获取任务,执行任务,通过将任务重新插入队列来安排任务的下一次执行,然后再次轮询队列。 如果队列中有任务,那就太好了。 如果没有,他们将等到下一个任务准备就绪(无论它当前在队列中还是以后添加)。 然后,他们重新启动整个过程。
综上所述,具有100个线程的ScheduledThreadPoolExecutor
可以轻松地以任何类型的速率处理100多个任务。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.