Threadpools können mehrere Aufgaben gleichzeitig ausführen. Manchmal möchten wir die Ausführungsergebnisse von Aufgaben verfolgen. Selbst innerhalb eines bestimmten Zeitraums möchten wir, wenn die Aufgabe nicht erledigt ist, die Ausführung von Aufgaben möglicherweise stornieren. Um diese Funktion zu unterstützen, bietet ThreadPoolexecutor FutureTask für die Verfolgung der Ausführung und Stornierung von Aufgaben. In diesem Artikel wird das Implementierungsprinzip von Futuretask eingeführt.
Um das Implementierungsprinzip von Futuretask besser zu verstehen, stellen wir zunächst mehrere wichtige Schnittstellen und Klassenstrukturen bereit, wie in der folgenden Abbildung gezeigt:
ThreadPoolexecutor stellt die Senden -Schnittstelle zum Senden von Aufgaben zur Verfügung. Senden unterstützt zwei verschiedene Schnittstellen: Runnable und Callable. Um eine einheitliche externe Schnittstelle bereitzustellen, wickelt JDK intern in einen Callable, das alle über den Runnableadapter -Adapter implementiert werden. Das Folgende ist der Quellcode von Runnableadapter:
Statische endgültige Klasse Runnableadapter <T> Implementiert Callable <T> {endgültige Runnable -Aufgabe; endgültiges T -Ergebnis; RunnableAdapter (Runnable Task, T -Ergebnis) {this.task = task; this.Result = Ergebnis; } public t call () {task.run (); Rückgabeergebnis; }}Runnableadapter ist die Implementierungsklasse von Callable, die die Anrufmethode implementiert. Die Anrufmethode ruft einfach Task.run () auf und gibt dann das Ergebnis zurück, wodurch nur die Callable -Schnittstelle gleichmäßig intern behandelt werden muss.
Im vorherigen Abschnitt wissen wir, dass die eingereichte Runnable -Aufgabe intern in Callable -Aufgaben umgewandelt wird. Überprüfen Sie den Rückgabewert der Subies -Methode, die eine Zukunft ist. Tatsächlich ist diese Zukunft eine Futuretask -Instanz. Durch diese Instanz kann das Aufrufen der GET -Methode den aktuellen Thread blockieren, bis die Aufgabe abgeschlossen ist und das Ergebnis zurückgegeben wird.
Die gesamte Anrufkette sieht so aus:
Worker Thread -> futuretask.run () -> Callable.call () -> Task.run ()
Wenn die aufrufbare Aufgabe eingereicht wird, gibt es nur die ersten drei Anrufe.
Um den gesamten Prozess besser zu demonstrieren, werden die folgenden Beispiele verwendet, um den Ausführungsprozess zu demonstrieren.
1. Senden Sie eine Callable -Aufgabe in den Thread -Pool (runnable wird ebenfalls in Callable konvertiert). Zu diesem Zeitpunkt wird der Callable in eine Futuretask -Instanz übergeben, wie unten gezeigt:
2. Der Thread -Pool verwendet einen Thread, um die Futuretask -Aufgabe auszuführen.
Der Prozess der Ausführung von Aufgaben ist relativ einfach. Am Ende wird die Methode callable.call () oder runnable.run () aufgerufen und ein Ergebnis erzielt, das das Ergebnis in der Ergebniseigenschaft der Futuretask -Instanz speichert, und der Status wird an normal geändert, was darauf hinweist, dass die Aufgabe ausgeführt wurde und das Ergebnis erhalten werden kann.
Wir gehen davon aus, dass mehrere Threads während der Ausführung von callable.call() die GET -Methode derselben Futuretask -Instanz aufrufen. Zu diesem Zeitpunkt werden diese Threads in einem Stapel blockiert und gespeichert, wie in der folgenden Abbildung gezeigt:
Threads 1, 2 und 3 rufen Sie FutureTask.get -Methode auf. Da die Aufgabe nicht ausgeführt wurde, werden alle drei Threads blockiert und schläfrig. Es gibt einen Stapel in Futuretask, um Wartefäden zu speichern. Der oberste Zeiger des Stacks wird von FutureTask.waiters verwiesen. Wenn die Aufgabe ausgeführt wird, werden die Threads im gesamten Stapel iteriert. Zu diesem Zeitpunkt wird jeder Thread geweckt und das Ergebnis der Aufgabenausführung kann erfolgreich erzielt werden (das Ausführungsergebnis wird in FutureTask.outcome) .
Futuretask unterstützt auch die Stornierungsfunktion von Aufgaben, die alle mehrere Threads über den Status von Futuretask koordinieren.
Die Futuretask -Schnittstelle ist ein Implementierungsmechanismus, der uns die Verfolgung und Kontrolle der Ausführung von Aufgaben ermöglicht. Im Vergleich zum Fadenpool selbst ist es relativ einfach und ich glaube, es ist nicht schwer zu verstehen.
Das obige ist der gesamte Inhalt dieses Artikels über das Implementierungsprinzip von Futuretask im Java -Thread -Pool. Ich hoffe, es wird für alle hilfreich sein. Interessierte Freunde können weiterhin auf andere verwandte Themen auf dieser Website verweisen. Wenn es Mängel gibt, hinterlassen Sie bitte eine Nachricht, um darauf hinzuweisen. Vielen Dank an Freunde für Ihre Unterstützung für diese Seite!