Il est vaguement lié à cette question: Êtes std::thread pool en C++11?. Bien que la question est différente, l'intention est la même:
Question 1: Est-il encore un sens à l'utilisation de votre propre (ou de la 3e partie de la bibliothèque) des pools de threads pour éviter de coûteux de création de thread?
La conclusion dans l'autre question est que vous ne pouvez pas compter sur std::thread
à être mis en commun (il peut ou peut être pas). Toutefois, std::async(launch::async)
semble avoir beaucoup plus de chances d'être mises en commun.
Il ne pense pas qu'il y est forcé par la norme, mais à mon humble avis je m'attends à ce que tout bon C++11 implémentations serait d'utiliser du fil de mise en commun si la création de threads est lente. Uniquement sur les plates-formes où il est peu coûteux de créer un nouveau fil de discussion, je m'attends à ce qu'ils ont toujours générer un nouveau thread.
Question 2: C'est juste ce que je pense, mais je n'ai pas faits pour le prouver. Je peut très bien se tromper. Est-ce une supposition?
Enfin, ici, j'ai fourni un exemple de code qui montre d'abord comment je pense que la création de threads peuvent être exprimées en async(launch::async)
:
Exemple 1:
thread t([]{ f(); });
// ...
t.join();
devient
auto future = async(launch::async, []{ f(); });
// ...
future.wait();
Exemple 2: Fire and forget fil
thread([]{ f(); }).detach();
devient
// a bit clumsy...
auto dummy = async(launch::async, []{ f(); });
// ... but I hope soon it can be simplified to
async(launch::async, []{ f(); });
Questin 3: préférez-vous l' async
versions de l' thread
versions?
Le reste n'est plus une partie de la question, mais seulement pour la clarification:
Pourquoi faut-il le retour de la valeur affectée à une variable fictive?
Malheureusement, l'actuel C++11 standard des forces de l'acquisition de la valeur de retour de l' std::async
, sinon le destructeur est exécutée, ce qui bloque jusqu'à ce que l'action se termine. Il est considéré comme une erreur dans la norme (p. ex., par Herb Sutter).
Cet exemple de l' cppreference.com l'illustre bien:
{
std::async(std::launch::async, []{ f(); });
std::async(std::launch::async, []{ g(); }); // does not run until f() completes
}
Une autre précision:
Je sais que les pools de threads peuvent avoir d'autres legimate utilise, mais dans cette question, je ne suis qu'intéressantes, à l'aspect d'éviter de coûteuses de création de thread coûts.
Je pense qu'il y a encore des situations où les pools de threads sont très utiles, surtout si vous avez besoin de plus de contrôle sur les ressources. Par exemple, un serveur peut décider de traiter qu'un nombre fixe de demandes simulatenously pour garantir des temps de réponse rapide et d'accroître la prévisibilité de l'utilisation de la mémoire. Les pools de threads doit être fine, ici.
Ces variables peuvent aussi être un argument pour votre propre pools de threads, mais je ne suis pas sûr de savoir si c'est conditions dans la pratique:
- La création d'un nouveau thread avec
std::thread
démarre sans initialisé les variables locales de thread. Peut-être que ce n'est pas ce que vous voulez. - Dans les fils engendré par
async
, il est peu claire pour moi parce que le fil aurait pu être réutilisés. De ma compréhension, ces variables ne sont pas garantis pour être remises à zéro, mais je me trompe peut-être. - À l'aide de votre propre (de taille fixe) des pools de threads, d'autre part, vous donne le plein contrôle si vous en avez vraiment besoin.