web-dev-qa-db-fra.com

quelle est la bonne façon d'utiliser un ThreadPool?

Si ma compréhension du fonctionnement de ThreadPool est correcte, l'un de ses objectifs est de limiter le nombre de threads de travail dans un processus pouvant être créés à un moment donné. Par exemple, si vous définissez MaxThreads sur 5, puis appelez QueueUserWorkItem 30 fois, 30 demandes seront envoyées au ThreadPool, mais seules 5 de ces demandes seront traitées par un nouveau thread, tandis que les 25 autres seront ajoutées à la file d'attente. et traité un à un à mesure que les demandes précédentes sont terminées et que les threads existants deviennent disponibles.

Dans le code ci-dessous, toutefois, l'appel à Thread.Sleep (-1) garantit que la méthode DoSomething () ne sera jamais renvoyée, ce qui signifie que le thread actuel ne sera jamais disponible pour les requêtes suivantes.

Mais ma compréhension du fonctionnement d'un ThreadPool ne peut pas être correcte, car si c'était le cas, le code ci-dessous n'indiquerait que les chiffres 0-4, plutôt que 0-29.

Quelqu'un peut-il expliquer s'il vous plaît comment fonctionne ThreadPool et pourquoi le code ci-dessous ne fait pas ce que je pensais qu'il devrait faire?

    static void DoSomething(object n)
    {
        Console.WriteLine(n);
        Thread.Sleep(-1);
    }

    static void Main(string[] args)
    {
        ThreadPool.SetMaxThreads(5, 5);
        for (int x = 0; x < 30; x++)
        {
            ThreadPool.QueueUserWorkItem(new WaitCallback(DoSomething), x);
        }
        Console.Read();
    }
23
John Smith

Mais ma compréhension de la façon dont fonctionne un ThreadPool ne peut pas être correcte, parce que s'il était correct, le code ci-dessous n'indiquerait que les nombres 0-4, plutôt que 0-29.

Oui, votre hypothèse est tout à fait correcte.

Etant donné que vous avez mis en file d'attente 30 tâches dans un ThreadPool et que les tâches seront suspendues pour InfiniteTime, elles ne se termineront jamais. La classe ThreadPool attendra un certain intervalle pour créer un nouveau thread, sans toutefois dépasser le nombre maximal de threads.

REMARQUE

Console.Read () garde votre thread d'arrière-plan actif.

Des articles

À partir de MSDN

De nombreuses applications créent des threads qui passent beaucoup de temps dans l'état de sommeil, attendant qu'un événement se produise. D'autres discussions pourraient n'entrez dans un état de sommeil que pour être réveillé périodiquement afin de rechercher un changer ou mettre à jour les informations d'état. Le regroupement de threads vous permet d'utiliser threads plus efficacement en fournissant à votre application un pool de les threads de travail gérés par le système. Un thread surveille le état de plusieurs opérations d'attente mises en file d'attente dans le pool de threads. Lorsqu'un opération d'attente terminée, un thread de travail du pool de threads exécute la fonction de rappel correspondante.


Lorsque tous les threads du pool de threads ont été affectés à des tâches, le thread Le pool ne commence pas immédiatement à créer de nouveaux threads inactifs. Éviter allouant inutilement de l’espace de pile pour les threads, il crée un nouveau inactif fils à intervalles. L'intervalle est actuellement d'une demi-seconde, bien que cela puisse changer dans les futures versions du .NET Framework.


Les threads du pool de threads gérés sont des threads d'arrière-plan. Cette est, leurs propriétés IsBackground sont vraies. Cela signifie qu'un ThreadPool thread ne gardera pas une application en cours d'exécution après tout les fils de premier plan sont sortis.

4
PaRiMaL RaJ

Il se peut que Thread.Sleep (-1) ne fasse pas ce que vous attendez. 

Paramètre Int32: Le nombre de millisecondes pendant lequel le thread est bloqué. Spécifiez zéro (0) pour indiquer que ce thread doit être suspendu pour permettre à d'autres threads en attente de s'exécuter. Spécifiez Infinite pour bloquer le thread indéfiniment.

http://msdn.Microsoft.com/en-us/library/d00bd51t.aspx

Vous devriez examiner les tâches, http://msdn.Microsoft.com/en-us/library/dd235608.aspx Pensez-y comme Threadpool 2.0

2
Austin Harris

En règle générale, ThreadPool crée un nombre de threads égal au nombre de cœurs de processeur. Il n’est pas nécessaire de créer plus de threads, un seul thread pouvant être traité par le noyau à la fois. Mais, lorsque la tâche mise en file d'attente dans un ThreadPool nécessite plus de 0,5 seconde pour s'exécuter, le ThreadPool crée un thread supplémentaire pour gérer les tâches restantes dans une file d'attente. Donc, si vous mettez beaucoup de tâches lourdes en file d'attente dans un ThreadPool, cela créera beaucoup de threads supplémentaires pour émuler le multitâche et exécuter toutes les tâches en parallèle. Mais le temps d'exécution total serait le même que s'il n'y avait pas de threads supplémentaires. De plus, il le serait encore moins parce que la création du thread est une opération assez lourde. C'est pourquoi ThreadPool est recommandé pour les petites tâches afin d'éviter la création de threads supplémentaires qui ne présentent aucun avantage.

Vous pouvez en savoir plus sur ThreadPool dans Albahari's article. En fait, il y a de nombreux articles sur le filetage.

0