Advanced   Java   Services Executors.newScheduledThreadPool(int) Back Next Up Home


Executors.newScheduledThreadPool(int)

Der zurückgegebene ScheduledExecutorService ist ein vollwertiger ScheduledThreadPoolExecutor wie der Quellcode zeigt.

public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) {
        return new ScheduledThreadPoolExecutor(corePoolSize);
}

Damit ist die Queue wie zuvor eine BlockingQueue<Runnable> und wird realisiert durch die statische innere Klasse ScheduledThreadPoolExecutor$DelayedWorkQueue

/**
 * Specialized delay queue. To mesh with TPE declarations, this
 * class must be declared as a BlockingQueue<Runnable> even though
 * it can only hold RunnableScheduledFutures.
 */
static class DelayedWorkQueue extends AbstractQueue<Runnable>
    implements BlockingQueue<Runnable> {

Ebenso ist die ThreadFactory wie bei allen Executoren die packageprivate statische innere Klasse DefaultThreadFactory der Factoryklasse Executors.


Single shots

Für single shots reicht ein ExecutorService mit einem ThreadPool der Größe eins, siehe also die vorigen Beispiele.


Wiederholte shots

ScheduleWithFixedDelay

Die Arbeitsweise dieses Algorithmus ist natürlich dieselbe wie im vorigen Beispiel, man kann höchstens fragen, ob bei einem größeren Pool verschiedene Threads arbeiten.

Um das zu klären, variieren wir das entprechend vorige Beispiel und definieren einen ThreadPool der Größe drei

private static void periodicShot_FixedDelay_ScheduledThreadPool()
{
  ScheduledExecutorService stse = Executors.newScheduledThreadPool(3);

  ...

  stse.scheduleWithFixedDelay(ru, 2, 3, TimeUnit.SECONDS);

  ...
}

Das Ergebnis kann folgendermaßen aussehen

Executors-ScheduledExecutorService
ScheduledThreadPool starts at 2016-03-21T14:12:36.999
pool-1-thread-1 start: 2016-03-21T13:12:39.009Z
pool-1-thread-1 duration: 2
pool-1-thread-1 end: 2016-03-21T13:12:41.024Z

pool-1-thread-1 start: 2016-03-21T13:12:44.025Z
pool-1-thread-1 duration: 2
pool-1-thread-1 end: 2016-03-21T13:12:46.025Z

pool-1-thread-2 start: 2016-03-21T13:12:49.026Z
pool-1-thread-2 duration: 2
pool-1-thread-2 end: 2016-03-21T13:12:51.026Z

pool-1-thread-2 start: 2016-03-21T13:12:54.028Z
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:12:58.028Z

pool-1-thread-2 start: 2016-03-21T13:13:01.029Z
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:13:05.029Z

shutdown
end main

Zwar gibt es zwei Threads, aber sie können nur nacheinander laufen.


ScheduleAtFixedRate

Hier interessiert nur die Frage, ob es sich überlappende Threads gibt um Verzögerungen zu vermeiden.

Wiederum ändern wir in unserem Beispiel nur eine Zeile

private static void periodicShot_FixedDelay_ScheduledThreadPool()
{
  ScheduledExecutorService stse = Executors.newScheduledThreadPool(3);

  ...

  stse.scheduleWithFixedDelay(ru, 2, 3, TimeUnit.SECONDS);

  ...
}

Ein möglicher Ablauf

Executors-ScheduledExecutorService
ScheduledThreadPool starts at 2016-03-21T14:42:19.349
pool-1-thread-1 start: 2016-03-21T13:42:21.359Z  //  21  +0
pool-1-thread-1 duration: 2
pool-1-thread-1 end: 2016-03-21T13:42:23.374Z

pool-1-thread-1 start: 2016-03-21T13:42:24.359Z  //  24  +0
pool-1-thread-1 duration: 2
pool-1-thread-1 end: 2016-03-21T13:42:26.359Z

pool-1-thread-2 start: 2016-03-21T13:42:27.359Z  //  27  +0
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:42:31.359Z

pool-1-thread-2 start: 2016-03-21T13:42:31.359Z  //  30  +1
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:42:35.359Z

pool-1-thread-2 start: 2016-03-21T13:42:35.359Z  //  33  +2
pool-1-thread-2 duration: 2
pool-1-thread-2 end: 2016-03-21T13:42:37.360Z

pool-1-thread-2 start: 2016-03-21T13:42:37.360Z  //  36  +1
pool-1-thread-2 duration: 2
pool-1-thread-2 end: 2016-03-21T13:42:39.360Z

pool-1-thread-2 start: 2016-03-21T13:42:39.360Z  //  39  +0
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:42:43.360Z

pool-1-thread-2 start: 2016-03-21T13:42:43.360Z  //  42  +1
pool-1-thread-2 duration: 4
pool-1-thread-2 end: 2016-03-21T13:42:47.360Z

pool-1-thread-2 start: 2016-03-21T13:42:47.360Z  //  45  +2
pool-1-thread-2 duration: 2
shutdown
end main
pool-1-thread-2 end: 2016-03-21T13:42:49.360Z

Es laufen zwei Threads, aber wie bei einem SingleThreadPool laufen die Threads nicht überlappend und es wird versucht die vorlorene Zeit aufzuholen.













Valid XHTML 1.0 Strict top Back Next Up Home