Accueil Blog (en) Réflexions sur le développement - Permettez-moi d’IEnumerate les raisons

Réflexions sur le développement - Permettez-moi d’IEnumerate les raisons

Patrick Chen | 13 avril 2021

Réflexions sur le développement - Permettez-moi d’IEnumerate les raisons

Récemment, je travaillais sur un morceau de code particulièrement complexe qui nécessitait beaucoup de manipulation de données, de regroupement, de tri, etc. et j’ai eu une percée qui, je l’espère, peut s’avérer utile pour d’autres développeurs.

En règle générale, lorsque j’extrait des données d’Acumatica, je suis à l’aise d’extraire des données dans des objets PXResultSet et de parcourir les résultats en boucle dans une boucle Foreach .  Ce modèle est généralement suffisant pour la plupart des tâches.  La nouvelle tâche, cependant, a nécessité beaucoup de traitement des données plutôt que de simplement énumérer à travers la liste.  En outre, les performances étaient une préoccupation, donc je voulais minimiser le nombre de fois que je suis allé à la couche de données.  Pour ces deux raisons, je voulais garder mes données indépendantes du cache.  Ce que je devais faire était d’extraire des données dans un objet IEnumerable , puis de les parcourir en boucle, de les filtrer, de les copier et de les manipuler via des opérations LINQ .  Au départ, j’ai eu du mal à obtenir PXResultSets dans une liste. Je n’ai pas pu le traduire directement dans la liste dont j’avais besoin.  Ensuite, j’ai découvert ce qui suit dans le code source.

Var ListofLines = SelectFrom<SOShipLine>.View.Select(this).RowCast<SOShipLine>().ToList();

L’appel RowCast refactorise le PXResultSet dans une liste des objets que vous transmettez dans l’appel.  Si vous ne connaissez pas la technologie, c’est le bon moment pour rafraîchir votre nomenclature C # LINQ.  Je trouve que la manipulation des données dans la couche application a été un grand gain d’efficacité en termes d’achèvement des tâches de programmation et de gains de performance du système.  Je trouve deux scénarios communs dans mon code où ce modèle peut apporter des avantages.

Scénario un : Prédicats BQL compliqués

Plutôt que de formuler des prédicats BQL compliqués qui regroupent par, additionnez, calculent, etc. je vide un ensemble de données dans une liste et le manipule via LINQ.  Ceci est particulièrement utile si vous recherchez des données plusieurs fois par rapport au même DAC.  Il est certainement plus lisible qu’une longue déclaration BQL .  Dans le code ci-dessous, la méthode I est un motif typique tiré de la source Acumatica.  La méthode II est une version qui extrait les données avec une clause Where mais laisse le regroupement dans la couche d’application.  L’avantage ici est que j’ai également pu facilement obtenir un décompte distinct et que je peux ensuite me référer facilement aux données non groupées d’origine.  Il est également possible que des gains de performance puissent être réalisés en fonction de la charge /architecture du système de l’instance particulière d’Acumatica.

GIST : https://gist.github.com/patrick711/bea38c39e1324c20cae5c56cddba6e9f

Scénario deux : Ensembles de données

Je pense qu’à mesure que votre code devient complexe, il est important de prendre en compte les besoins en données de l’ensemble de code d’un point de vue descendant.  Lors du codage de tâches compliquées, il est facile de se laisser prendre dans les mauvaises herbes et de vous retrouver à interroger le même DAC plusieurs fois pour accomplir des tâches distinctes.  Cela peut être particulièrement vrai si vous êtes doué pour écrire des blocs de code modulaires.  L’un des moyens les plus simples de repérer cela est de penser à mettre à jour les boucles imbriquées.  Si vous avez une boucle imbriquée qui extrait des données, un Foreach typique avec un PXSelect, il déclenchera le PXSelect chaque fois que la boucle supérieure itère.  Plutôt que d’itérer un appel de couche de données chaque fois que vous pouvez envisager d’extraire un ensemble de données plus grand une fois au-dessus de la boucle et de filtrer vers le bas de l’ensemble pour chaque itération de boucle. Dans la méthode II ci-dessous, j’extrait un ensemble de comptes avec des comptes parents avant le début de la boucle.  Mais attendez, vous pouvez demander, pourquoi ne pas tirer tous les comptes pour les deux boucles?  Cela peut être génial, surtout si vous avez besoin de ces données pour d’autres tâches ou si vous avez une bonne idée de l’ensemble de données résultant.  Il peut également extraire un grand ensemble de données inutile qui effacerait tous les gains de performances que vous pourriez faire.  Comme toujours, il est important de prendre en compte la topologie de vos données.

GIST: https://gist.github.com/patrick711/49a7a0e361f0acb17742f162da16e773

Ces exemples sont présentés comme un moyen de rendre le code plus lisible, de tirer parti des capacités C # natives et potentiellement de trouver des efficacités de performance.  J’espère que c’était utile, bon codage!

Auteur du blog

Patrick est le développeur principal de SPS Commerce EDI pour Acumatica. Il est un développeur Acumatica entièrement certifié et travaille avec le produit depuis 2013. Il a plus de 17 ans de développement de logiciels personnalisés dans l’industrie ERP.

Recevez des mises à jour de blog dans votre boîte de réception.