C# ont async appel de fonction de fonction synchrone ou un appel de fonction synchrone asynchrone en fonction de
Je suis en train d'écrire un C# .Net 4.5 bibliothèque pour faire commun sql opérations de base de données (sauvegarde, restauration, exécuter le script, etc.). Je veux avoir à la fois synchrone et asynchrone des fonctions pour chaque opération, cette bibliothèque sera utilisé par la console et des applications à interface graphique, mais je ne veux pas de code dupliqué partout. Donc, comme je le vois, j'ai deux options:
- Écrire le code qui fait le travail dans une fonction synchrone, et puis il suffit de l'envelopper dans une tâche asynchrone en fonction, comme suit:
public void BackupDB(string server, string db) { //Do all of the work and long running operation here } public async Task BackupDBAsync(string server, string db) { await Task.Factory.StartNew(() => BackupDB(server, db)).ConfigureAwait(false); }
- Écrire le code qui fait le travail dans une fonction d'asynchrone, et de l'appeler à partir d'une fonction synchrone à l'aide .Wait():
public async Task BackupDBAsync(string server, string db) { //Do all of the work and long running operation here, asynchronously. } public void BackupDB(string server, string db) { BackupDBAsync(server, db).Wait(); //Execution will wait here until async function finishes completely. }
Est une option meilleure que l'autre? Est l'une des meilleures pratiques? Ou existe-il d'autres (mieux) les solutions de rechange?
Je sais qu'une mise en garde à l'aide .Wait() est que tous les attendent des instructions dans la fonction async .ConfigureAwait(faux) pour éviter les blocages (comme discuté ici), mais depuis que je suis en train d'écrire une bibliothèque qui n'auront jamais besoin d'accéder à l'INTERFACE utilisateur ou WebContext je suis sûre de le faire.
Je note aussi que le SQL bibliothèque sont généralement aussi a la fois synchrone et asynchrone des fonctions qui peuvent être utilisées, donc si vous faites le travail dans la fonction de synchronisation, je dirais que leur fonction de synchronisation, et si vous faites le travail dans la fonction async, je dirais que leur fonction async.
Idées/suggestions sont les bienvenues.
-- edit: j'ai aussi posté cette question sur les forums MSDN ici pour essayer et obtenir un fonctionnaire MS réponse --
Je suis généralement quelque chose qui est déjà écrit. Si ce que l'on ne prend pas en charge asynchrone à tous, alors je ferais votre exemple 1.
OriginalL'auteur deadlydog | 2012-07-26
Vous devez vous connecter pour publier un commentaire.
La meilleure réponse est: ne pas.
Stephen Toub a deux excellents posts de blog sur ce sujet:
Il recommande d'exposer des méthodes asynchrones asynchrones et synchrones méthodes synchrones. Si vous avez besoin d'exposer à la fois, puis encapsuler les fonctionnalités courantes dans le secteur privé (synchrone) méthodes et de dupliquer les async/sync différences.
J'aime aussi cette réponse n'est pas seulement pour les problèmes qu'il permet aux consommateurs de la bibliothèque éviter (comme mentionné ci-dessus), mais aussi il aide à prévenir le ballonnement dans ma bibliothèque, que j'allais créer synchrone et asynchrone versions de chaque fonction publique, dans ma bibliothèque, ce qui aurait aussi signifié double de la documentation et tous les autres maux de tête qui vont avec ayant 2 fonctions pour chaque opération.
OriginalL'auteur Stephen Cleary
J'ai eu une situation similaire, où certaines des applications les données à charger en mode synchrone et d'autres asyc. J'ai décidé de créé une interface que j'ai appelé mon dataloader:
La AssignProjects de rappel est juste un simple délégué qui prend dans la liste retournée de projets:
Maintenant, la beauté de ceci est que vous pouvez travailler avec l'interface sans savoir si vous êtes a affaire à de synchronisation ou asynchrone.
Trois classes sont créées: une base, une synchronisation et une async:
Maintenant, dans votre application, vous pouvez décider comment vous voulez charger les données...ce qui pourrait être injecté dans un conteneur IoC, mais est codé en dur à des fins de démonstration:
Maintenant, votre code d'appel a la même apparence et n'est pas plus sage de savoir s'il est asynchrone ou de synchronisation:
J'utilise régulièrement pour les tests unitaires (sync), les applications WPF (async), et les applications de console (sync).
OriginalL'auteur Josh
Il ne semble pas être un point de marquer simplement une méthode async sans l'aide d'un attendent. Le marquant comme async ne pas le faire asynchrone, il vous permet d'utiliser attend (le code exécuté dans l'attendent est ce qui se passe de manière asynchrone, et puis le reste de la méthode asynchrone peut aussi être effectuée de manière asynchrone) dans le corps de la méthode:
Généralement, une méthode modifiée par la async mot-clé contient au moins une attendent de l'expression ou de la déclaration. La méthode s'exécute de façon synchrone jusqu'à ce qu'il atteigne la première attendent expression, à laquelle il est suspendu jusqu'à ce que l'attendu de la tâche est terminée. Dans l'intervalle, le contrôle est retourné à l'appelant de la méthode. Si la méthode ne contient pas attendre de l'expression ou de l'instruction, puis il s'exécute en mode synchrone. Un avertissement du compilateur vous signale les méthodes asynchrones qui ne contiennent pas d'attendre car cette situation pourrait indiquer une erreur. Pour plus d'informations, voir l'Avertissement du Compilateur CS4014.
À partir de: asynchrone
Corriger Pierre, je serais en attente la fonction SQL server appels qui fait exécuter l'opération de sauvegarde, de restauration, d'exécuter le script, etc.), étant donné que ce travail sera fait par le serveur de base de données, pas de ma bibliothèque de processus (par exemple, mon PC juste attend pour une opération sur un autre PC pour être complète; il n'a pas le craquement lui-même).
OriginalL'auteur Stefan H