La création d'une dynamique (croissance/réduire) le pool de thread
J'ai besoin de mettre en œuvre un pool de threads en Java (java.util.simultanées), dont le nombre de threads est à une certaine valeur minimale lorsqu'il est inactif, pousse jusqu'à une limite supérieure (mais jamais plus) lorsque les travaux sont soumis en plus rapidement qu'ils ne le fini de l'exécution, et se rétrécit en arrière de la limite inférieure quand tous les travaux sont effectués et non plus de travaux sont soumis.
Comment voulez-vous mettre en place quelque chose comme ça? J'imagine que ce serait un assez commune scénario d'utilisation, mais apparemment le java.util.concurrent.Executors
usine méthodes ne peuvent créer de taille fixe, de piscines et de bassins que croître indéfiniment lorsque de nombreux travaux sont soumis. Le ThreadPoolExecutor
classe fournit corePoolSize
et maximumPoolSize
paramètres, mais sa documentation semble impliquer que la seule façon de jamais avoir plus de corePoolSize
threads en même temps est d'utiliser un délimitée de la file d'attente de travail, auquel cas, si vous avez atteint maximumPoolSize
threads, vous obtiendrez les rejets qui vous avez à traiter avec vous-même? Je suis venu avec cette:
//pool creation
ExecutorService pool = new ThreadPoolExecutor(minSize, maxSize, 500, TimeUnit.MILLISECONDS,
new ArrayBlockingQueue<Runnable>(minSize));
...
//submitting jobs
for (Runnable job : ...) {
while (true) {
try {
pool.submit(job);
System.out.println("Job " + job + ": submitted");
break;
} catch (RejectedExecutionException e) {
//maxSize jobs executing concurrently atm.; re-submit new job after short wait
System.out.println("Job " + job + ": rejected...");
try {
Thread.sleep(300);
} catch (InterruptedException e1) {
}
}
}
}
Suis-je surplombant quelque chose? Est-il une meilleure façon de le faire? Aussi, selon les besoins, il peut être contestable que le code ci-dessus ne seront pas finir au moins jusqu'à (je pense) (total number of jobs) - maxSize
emplois ont fini. Donc, si vous voulez être en mesure de présenter un nombre arbitraire d'emplois dans la piscine et de procéder immédiatement, sans attendre que l'un d'eux pour finir, je ne vois pas comment vous pourriez le faire sans avoir un "emploi sumitting" thread qui gère le nécessaire de la surabondance de la file d'attente pour contenir les emplois. AFAICS, si vous utilisez une surabondance de la file d'attente pour le ThreadPoolExecutor lui-même, son nombre de thread ne sera jamais pousser au-delà de corePoolSize.
Pourquoi est -
newCachedThreadPool
ne convient pas à votre situation? Automatiquement, il tue les threads qui ne sont plus utilisés.Ce qui serait si votre threads inactifs n'est pas mort? Disons que vous avez eu une taille fixe de la piscine de la taille maximale de tous les temps? Qu'arriverait-il?
AFAICS, newCachedThreadPool crée un pool dont le nombre de threads peut croître sans limites si vous envoyez de nombreux travaux en cours d'exécution.
Non, le nombre de processeurs ne changera pas lors de l'exécution, mais je ne vois pas en quoi c'est pertinent si les travaux sont largement dépendant des e/S plutôt qu'en CPU. Dans ce cas, vous permettent d'augmenter le débit par l'utilisation de plusieurs threads, même sur un système monoprocesseur.
OriginalL'auteur Olaf Klischat | 2012-06-28
Vous devez vous connecter pour publier un commentaire.
Un truc qui pourrait vous aider à assigner un
RejectedExecutionHandler
qui utilise le même fil de soumettre le travail dans la file d'attente de blocage. Qui permet de bloquer le thread courant et de supprimer la nécessité pour une sorte de boucle.Voir ma réponse ici:
Voici le rejet gestionnaire copié à partir de cette réponse.
Vous devriez alors être en mesure de faire usage de la core/max du nombre de thread aussi longtemps que vous vous rendez compte que la délimitée bloque la file d'attente que vous utilisez première se remplit avant tout les threads sont créés au-dessus de la base de threads. Donc, si vous avez 10 de base de threads et vous souhaitez le 11 emploi pour démarrer la 11e fil, vous aurez besoin d'avoir une file d'attente de blocage avec une taille de 0 malheureusement (peut-être un
SynchronousQueue
). J'ai l'impression que c'est une réelle limitation dans l'autre grandeExecutorService
classes.OriginalL'auteur Gray
Lors de la croissance et de la réduction de vient avec le fil, il n'y a qu'un seul nom qui me vient à l'esprit: CachedThreadPool à partir de java.util.simultanées paquet.
CachedThreadPool() peut réutiliser le fil, ainsi que créer de nouveaux threads lorsque nécessaire.
Et oui, si un thread est inactif pendant plus de 60 secondes, CachedThreadPool le tuera. Donc, c'est assez léger, la croissance et une diminution de la vos mots!
Vous pouvez utiliser des sous-jacents ThreadPoolExecutor et d'installation maximumPoolSize manuellement ou même au moment de l'exécution
OriginalL'auteur Kumar Vivek Mitra
Ensemble
maximumPoolSize
àInteger.MAX_VALUE
. Si jamais vous avez plus de 2 milliards de discussions...eh bien, bonne chance avec ça.De toute façon, la Javadoc de
ThreadPoolExecutor
états:Avec la même surabondance de la tâche de la file d'attente comme un
LinkedBlockingQueue
, ce qui devrait avoir arbitrairement grande capacité.Merci de consulter cette stackoverflow.com/questions/28567238/... rétrécissement de frapper d'autres problèmes résolus dans d'autres question
il voulait de l'avoir délimité, pas illimitée...
OriginalL'auteur Louis Wasserman