2012-04-30 11 views
33

In Fortsetzung zu einem question von mir gepostet, versuche ich ThreadPoolExecutor in meiner Codebasis zu verwenden. Selbst nach wiederholten Versuchen, das Java-API-Dokument zu verstehen, konnte ich die Funktionalität/den Zweck hinter dem keepAliveTime-Parameter, der im Konstruktor übergeben werden soll, nicht klar verstehen. Hoffe jemand kann mir ein gutes Arbeitsbeispiel erklären.Wie funktioniert Keep-Alive mit ThreadPoolExecutor?

Auszüge aus Java doc:

public ThreadPoolExecutor(int corePoolSize, 
          int maximumPoolSize, 
          long keepAliveTime, 
          TimeUnit unit, 
          BlockingQueue<Runnable> workQueue) 

keepAliveTime - , wenn die Anzahl der Threads größer ist als der Kern ist, ist dies die maximale Zeit, die überschüssigen Leerlauf-Threads für neue Aufgaben warten vor dem Beenden.

+2

Genau wie ein Punkt der Terminologie zeigt, haben Sie zweimal das Wort „implementieren“, wenn ich glaube, Sie nur „Verwendung“ bedeutet. Sie versuchen nicht, * ThreadPoolExecutor * zu implementieren, indem Sie Ihren eigenen Code schreiben, der diese API implementiert - Sie erstellen gerade einen 'ThreadPoolExecutor' und wollen wissen, wie sich das verhält, richtig? –

+0

Ja, du hast Recht. Ich habe nur gesagt, dass es eine neue Art von Implementierung in meiner Codebasis ist. – Gnanam

+0

Aber es ist keine Implementierung * von * 'ThreadPoolExecutor'. Es ist sehr hilfreich, wenn Sie die Terminologie entsprechend verwenden können - * besonders * auf Stack Overflow. –

Antwort

47

Angenommen, Sie haben eine Kerngröße von 5 und eine maximale Größe von 15. Aus irgendeinem Grund wird Ihr Pool ausgelastet und verwendet alle 15 verfügbaren Threads. Irgendwann hast du keine Arbeit mehr - also werden einige deiner Threads untätig, wenn sie ihre letzte Aufgabe erledigt haben. Also dürfen 10 dieser Threads sterben.

Um zu vermeiden, dass sie zu schnell ausgeschaltet werden, können Sie die Keep-Alive-Zeit angeben. Wenn Sie also 1 als keepAliveTime Wert und TimeUnit.MINUTE als unit Wert angegeben haben, würde jeder Thread eine Minute warten, nachdem er eine Aufgabe beendet hat, um zu sehen, ob noch mehr Arbeit zu erledigen war. Wenn es noch keine Arbeit bekommen hätte, würde es sich vollenden lassen, bis es nur noch 5 Threads im Pool gäbe - den "Kern" des Pools.

+2

Wenn ich das richtig verstanden habe, wird "keepAliveTime" nur dann verwendet/wirksam, wenn Threads im Pool mehr als die Kerngröße haben. Dies ist * nicht * anwendbar, wenn Threads im Pool unterhalb der Kerngröße liegen. – Gnanam

+0

Sorry, wenn diese Frage zu einfach ist. Aber warum wollen wir Threads am Leben erhalten, die wirklich eine Aufgabe erledigt haben? Jedenfalls ist die maximale Anzahl von Threads ('maximumPoolSize'), die im Pool erlaubt sind, begrenzt, oder? – Gnanam

+2

Der Punkt, dass Threads gelöscht werden, ist derselbe wie der Punkt, an dem überhaupt ein Thread-Pool vorhanden ist - keine unnötigen Ressourcen zu verschwenden. –

3

Hier einige weitere Beschreibung aus der Javadoc:

<dt>Keep-alive times</dt> 
* 
* <dd>If the pool currently has more than corePoolSize threads, 
* excess threads will be terminated if they have been idle for more 
* than the keepAliveTime (see {@link 
* ThreadPoolExecutor#getKeepAliveTime}). This provides a means of 
* reducing resource consumption when the pool is not being actively 
* used. If the pool becomes more active later, new threads will be 
* constructed. This parameter can also be changed dynamically 
* using method {@link ThreadPoolExecutor#setKeepAliveTime}. Using 
* a value of <tt>Long.MAX_VALUE</tt> {@link TimeUnit#NANOSECONDS} 
* effectively disables idle threads from ever terminating prior 
* to shut down. 
* </dd> 
* 

Im Wesentlichen dies ermöglicht Ihnen nur die Anzahl der Threads im Ruhepool links zu steuern. Wenn Sie dies zu klein machen (für das, was Sie tun), werden Sie zu viele Threads erstellen. Wenn Sie es zu groß machen, werden Sie Speicher/Threads verbrauchen, die Sie nicht benötigen.