Ich habe einen ThreadPoolExecutor, der mit einer LinkedBlockingDequeue erstellt wurde, und ich möchte die zugrunde liegende Warteschlange bearbeiten, aber das Lesen in der Dokumentation macht mich sehr nervös.
Warteschlangenverwaltung
Die Methode getQueue () erlaubt den Zugriff auf die Arbeitswarteschlange zum Überwachen und Debuggen. Von der Verwendung dieser Methode für andere Zwecke wird dringend abgeraten. Zwei bereitgestellte Methoden, remove (java.lang.Runnable) und purge (), sind verfügbar, um bei der Speicherrückgewinnung zu helfen, wenn eine große Anzahl von Aufgaben in der Warteschlange abgebrochen wird.
Genauer gesagt möchte ich dazu in der Lage sein
Danke
getQueue()
gibt immer die genaue BlockingQueue<Runnable>
zurück, die Sie an die ThreadPoolExecutor
übergeben haben.
Die Sorge mit der Dokumentation ist, dass Sie leicht auf Probleme mit doppeltem Ausführen stoßen könnten, wenn Sie die Thread-Sicherheit von BlockingQueue
nicht garantieren können. Wenn Sie PriorityBlockingQueue
verwenden und nur remove
und add
(oder direkter offer
) verwenden, sind Sie sicher und können dies auch direkt von getQueue()
aus tun.
Mit anderen Worten, jedes Mal, wenn Ihr Signal Ihnen sagt, dass sich die Runnable
-Priorität geändert hat, sollten Sie remove
it und das Ergebnis der Entfernung überprüfen ( true
wenn entfernt) und nur wenn es war tatsächlich entfernt, dann sollten Sie es erneut hinzufügen. Sie können nicht garantieren, dass zwischen diesen Vorgängen nicht etwas abgerufen wird, aber Sie haben zumindest garantiert, dass Sie Runnable
nicht doppelt ausführen, was leicht passieren könnte, wenn Sie mit contains
- & gt; remove
- & gt; add
.
Entweder das, oder Sie können Ihre eigene Implementierung eines BlockingQueue
schreiben, das ein Comparator
verwendet (wie das PriorityBlockingQueue
), das die höchste Priorität findet, wenn es nach neuen Daten gefragt wird. Das klingt nach viel mehr Arbeit angesichts der verschiedenen beteiligten Schnittstellen.
Tags und Links java multithreading