2010-09-08 5 views
0

J'ai un nombre raisonnable d'enregistrements dans une table Azure que je tente de faire un peu le chiffrement des données une seule fois sur. Je pensais que je pourrais accélérer les choses en utilisant un Parallel.ForEach. Aussi parce qu'il y a plus de 1K enregistrements et que je ne veux pas me tromper avec des jetons de continuation moi-même, j'utilise un CloudTableQuery pour obtenir mon énumérateur. Mon problème est que certains de mes enregistrements ont été cryptés en double et j'ai réalisé que je ne suis pas sûr de la sécurité des threads renvoyés par l'énumérateur par CloudTableQuery.Execute(). Quelqu'un d'autre a-t-il eu de l'expérience avec cette combinaison?Peut-Parallel.ForEach être utilisé en toute sécurité avec CloudTableQuery

Répondre

1

Malgré mes efforts, je suis incapable de reproduire mon problème d'origine. Ma conclusion est donc qu'il est parfaitement OK pour utiliser Parallel.ForEach boucles avec CloudTableQuery.Execute().

1

Je serais prêt à parier que la réponse à Exécuter en retournant une implémentation IEnumerator sûre pour les threads est hautement improbable. Cela dit, cela ressemble à un autre cas pour le producer-consumer pattern.

Dans votre scénario spécifique, le thread d'origine appelé Execute lit les résultats séquentiellement et les place dans un BlockingCollection<T>. Avant de commencer à le faire, vous devez démarrer un Task distinct qui contrôlera la consommation de ces éléments en utilisant Parallel::ForEach. Maintenant, vous voudrez probablement aussi vous pencher sur l'utilisation de la méthode GetConsumingPartitioner de la bibliothèque ParallelExtensions afin d'être plus efficace puisque le partitionneur par défaut créera plus de surdébit que vous ne voulez dans ce cas. Vous pouvez lire plus à ce sujet de this blog post.

Un bonus supplémentaire d'utilisation BlockingCollection<T> sur une ConcurrentQueueu<T> première est qu'il offre la possibilité de set bounds qui peut aider à bloquer le producteur d'ajouter d'autres éléments à la collection que les consommateurs peuvent suivre. Vous devrez bien sûr faire quelques tests de performance pour trouver le point idéal pour votre application.

+0

Depuis que je pose cette question que j'ai eu la chance d'essayer de recréer le scénario que je ressentais et jusqu'à présent, je suis incapable de reproduire le problème (comme il a été non répétable Je n'ai pas été en mesure de donner Beaucoup d'attention). Ce que vous proposez assurera certainement que ce n'était pas un problème. J'aimerais faire d'autres recherches pour voir si cet effort supplémentaire est requis. – knightpfhor

+0

Eh bien, honnêtement, je me rends compte que je me suis mal exprimé dans votre cas particulier. Parallel :: ForEach veillera à ce que l'énumérateur ne soit lu qu'à partir du thread initial par lots, puis les éléments individuels lus seront exportés vers des tâches programmées pour s'exécuter sur des threads potentiellement distincts. Vous n'avez donc pas besoin d'implémenter vous-même le modèle producteur-consommateur puisque vous avez déjà une source qui génère des éléments dans un flux (c'est-à-dire que IEnumerable de CloudTableQuery est retourné depuis execute). –

Questions connexes