英文:
Scheduled Executor Service with single thread
问题
以下是您要翻译的内容:
我有一个关于Scheduled Executor Service的示例代码,取自Oracle的网站。它创建了一个具有核心池大小为1的ScheduledExecutorService。它执行了两项任务:首先,在固定的时间间隔内启动一个重复的任务,然后在延迟后终止相同的任务和服务本身。
ScheduledExecutorService scheduledService = Executors.newScheduledThreadPool(1);
// 这将以固定的时间间隔执行任务
ScheduledFuture<?> futureTask = scheduledService.scheduleAtFixedRate(new RepeatedTask(), initialDelay, interval, TimeUnit.SECONDS);
// 返回一个Future任务,可以在一段时间后用于取消执行
// 在这里,我们将在100秒后取消重复的任务
scheduledService.schedule(new TaskStopper(futureTask, scheduledService), 100, TimeUnit.SECONDS);
重复的任务代码:
public class RepeatedTask implements Runnable{
int count = 0;
@Override
public void run() {
count++;
System.out.println(count + ". Beep");
}
}
终止任务:
@Override
public void run() {
mFutureTask.cancel(true);
System.out.println("Task stopped");
mExecutorService.shutdownNow();
boolean shutDown = mExecutorService.isShutdown();
if(shutDown) {
System.out.println("Executor shutdown");
}else {
System.out.println("Executor not shutdown");
}
}
我想要了解的是,它如何在线程池中使用单个线程。由于我们的执行器服务执行了两项几乎同时启动的任务,我们不应该拥有2个线程,即具有核心池大小为2的ScheduledExecutorService吗?
尽管如此,它运行得很好。我只是想要了解为什么它能在单个线程上正常运行。
英文:
I have a sample code for Scheduled Executor Service, taken from Oracle's site. It creates a ScheduledExecutorService with core pool size o 1. It does 2 jobs: First it starts a repeated task executed at fixed intervals and then it kills the same task and the service itself after a delay.
ScheduledExecutorService scheduledService = Executors.newScheduledThreadPool(1);
//This will keep executing the task at fixed interval
ScheduledFuture<?> futureTask = scheduledService.scheduleAtFixedRate(new RepeatedTask(), initialDelay, interval, TimeUnit.SECONDS);
//A future task is returned which can be used to cancel the execution after sometime
//Here we will cancel our repeated task after 100 seconds
scheduledService.schedule(new TaskStopper(futureTask, scheduledService), 100, TimeUnit.SECONDS);
The repeated task code:
public class RepeatedTask implements Runnable{
int count = 0;
@Override
public void run() {
count++;
System.out.println(count + ". Beep");
}
}
The stop task
@Override
public void run() {
mFutureTask.cancel(true);
System.out.println("Task stopped");
mExecutorService.shutdownNow();
boolean shutDown = mExecutorService.isShutdown();
if(shutDown) {
System.out.println("Executor shutdown");
}else {
System.out.println("Executor not shutdown");
}
}
I want to understand, how does it work with a single thread in the thread pool.
Since our executor service performs two tasks and starts them both almost at the same time,
shouldn't we have 2 threads i.e. a ScheduledExecutorService with core pool size of 2.
It works fine though. I just want to understand why it works fine with a single thread.
答案1
得分: 5
对于任何线程池(包括ScheduledThreadPool),线程的数量可以少于任务的数量。线程池内部有一个任务队列,在没有可用线程来执行任务时,任务将不得不等待。
在你的例子中,在 t=100 秒时,有两个任务需要执行。由于只有一个线程可用,它执行了第一个任务(第二个任务在队列中等待)。一旦第一个任务完成,线程从队列中取出第二个任务并完成它。
你可以在两个任务中都打印出线程 ID,并且可以验证它们确实由同一个线程处理。
编辑:
所以基本上,在固定的时间间隔内调度的任务会被多次执行,两次执行之间有固定的时间间隔。在这些间隔期间,线程池中的单个线程是空闲的,并且能够挑选其他任务来执行。这就是单个线程如何执行这两个任务的方式。
英文:
For any thread pool (including ScheduledThreadPool), number of threads can be less than number of tasks. Thread pools internally have a queue of tasks, in which a task will have to wait if no thread is available to execute the task.
In your example, at t=100 seconds, two tasks need to be executed. Since only one thread is available, it executes the first task (while second one waits in the queue). Once the first task is complete, the thread picks the second task from the queue and completes it.
You could print out the thread id in both the tasks and can verify that they are indeed being processed by the same thread.
Edit:
So basically the task scheduled at fixed interval is executed multiple times with fixed intervals in between. During these intervals, our single thread in the pool is idle and is able to pick other tasks for execution. That's how a single thread executes both the tasks.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论