Normalerweise, wenn man Java 8's parallelStream() verwendet, ist das Ergebnis die Ausführung über den standardmäßigen gemeinsamen Fork-Join-Pool (d. H. ForkJoinPool.commonPool()).Java parallelStream() mit benutzerdefinierten Pool mit Anrufer Arbeit stiehlt?
Dies ist jedoch eindeutig unerwünscht, wenn eine Arbeit vorliegt, die weit von der CPU entfernt ist, z. kann viel Zeit auf IO warten. In solchen Fällen möchte man einen separaten Pool verwenden, der nach anderen Kriterien bemessen ist (z. B. wie viel Zeit die Aufgaben wahrscheinlich tatsächlich mit der CPU verbringen).
Es gibt keine offensichtlich Mittel, um parallelStream() einen anderen Pool zu nutzen, aber es gibt einen Weg, wie detailliert here.
Leider führt dieser Ansatz dazu, die Terminal-Operation auf dem parallelen Stream von einem Fork-Join-Pool-Thread aufzurufen. Der Nachteil davon ist, dass, wenn der Target-Fork-Join-Pool vollständig mit vorhandener Arbeit beschäftigt ist, die gesamte Ausführung darauf wartet, während überhaupt nichts getan wird. Somit kann der Pool zu einem Engpass werden, der schlimmer ist als eine Einzel-Thread-Ausführung. Im Gegensatz dazu wird, wenn man parallelStream() in der "normalen" Art verwendet, ForkJoinPool.common.externalHelpComplete() oder ForkJoinPool.common.tryExternalUnpush() verwendet, um den aufrufenden Thread von außerhalb des Pools bei der Verarbeitung zu unterstützen.
Kennt jemand eine Möglichkeit, zu beide bekommt parallelStream() Pool einen Nicht-Standard-fork-join und von außerhalb der Gabel-join Pool Hilfe bei der Verarbeitung dieser Arbeit eine Berufung zu verwenden Thread (aber nicht der Rest der Gabel-Join-Pool-Arbeit)?
Ich verstehe nicht Ihre _Der Nachteil davon ist, dass wenn der Ziel-Gabel-Join-Pool vollständig mit vorhandenen Arbeit_ beschäftigt ist. Würden Sie nicht nur für diesen parallelen Stream-Aufruf einen neuen Pool erstellen? –
Es ist noch schlimmer. Wenn Sie bei Ihren Tasks 'get' aufrufen, die nicht im gemeinsamen Pool sind, wird' ForkJoinPool.common.tryExternalUnpush() 'aufgerufen, aber die Task wird nicht in der Warteschlange des gemeinsamen Pools gefunden. – Holger
Um die Frage zu beantworten, nein, ich würde nicht nur für diesen Aufruf einen neuen Thread-Pool erstellen. Eher würde ich diesen anderen Thread-Pool über viele ähnliche Aufrufe teilen, von denen einige sich überlappen könnten, von denen einige viel längere/größere Aufgaben haben könnten als andere usw. –