78 votes

Conseils pour optimiser les programmes C # / .NET

Il semble que l'optimisation est un art qui se perd de nos jours. N'était-il pas un moment où tous les programmeurs pressé chaque once de l'efficacité de leur code? Souvent de le faire lors de la marche de 5 km dans la neige?

Dans l'esprit de ramener un art perdu, ce sont quelques conseils que vous savez de pour de simples (ou peut-être complexe) des changements pour optimiser C#/.NET code? Depuis c'est comme un vaste chose qui dépend de ce que l'on essaie de réaliser qu'il faudrait aider à fournir un contexte avec le bout de votre. Par exemple:

  • Lors de la concaténation de plusieurs chaînes utiliser StringBuilder à la place. Voir le lien au bas des mises en garde sur ce point.
  • Utiliser string.Compare à comparer 2 chaînes au lieu de faire quelque chose comme string1.ToLower() == string2.ToLower()

Le consensus général jusqu'à ce jour semble être la mesure est la clé. Ce genre de manque à l'appel: la mesure n'est pas de vous dire ce qui ne va pas, ou ce qu'il faut faire à ce sujet si vous exécutez dans un goulot de bouteille. J'ai couru dans la concaténation de chaîne goulot de bouteille une fois et n'avait aucune idée de quoi faire à ce sujet, de sorte que ces conseils sont utiles.

De mon point de même ce détachement est d'avoir un endroit pour la commune de goulets d'étranglement et comment ils peuvent être évités avant même de courir en eux. Il n'est même pas nécessairement sur plug-and-play code que tout le monde devrait suivre aveuglément, mais plus sur la compréhension que la performance doit être pensé, au moins un peu, et qu'il y a certains pièges courants à regarder dehors pour.

Je vois bien qu'il pourrait être utile aussi de savoir pourquoi une astuce est utile et où elle devrait être appliquée. Pour l' StringBuilder astuce que j'ai trouvé de l'aide je l'ai fait il y a longtemps à ici sur Jon Skeet du site.

106voto

Eric Lippert Points 300275

Il semble que l'optimisation est un art qui se perd de nos jours.

Il était une fois un jour lors de la fabrication de, disons, des microscopes a été pratiqué comme un art. Les principes optiques ont été mal compris. Il n'y avait pas la direction de la standarisation des pièces. Les tubes et les engrenages et les lentilles devait être fabriqué à la main par des travailleurs hautement qualifiés.

Ces jours-ci, les microscopes sont produites comme une discipline technique. Les principes sous-jacents de la physique sont extrêmement bien comprises, hors-la-plateau de pièces sont largement disponibles, et le microscope de renforcement des ingénieurs peuvent faire des choix éclairés quant à la façon d'optimiser au mieux son instrument pour les tâches qu'il est conçu pour effectuer des.

Que l'analyse des performances est un "art perdu" est une très, très bonne chose. Que l'art était pratiqué comme un art. L'optimisation doit être abordée pour ce qu'il est: un problème d'ingénierie résoluble par une application rigoureuse de solides principes d'ingénierie.

J'ai été posée des dizaines de fois au fil des ans pour ma liste de "trucs et astuces" que les gens peuvent utiliser pour optimiser leur vbscript / leur jscript / active server pages / leur VB / leur code C#. J'ai toujours résister à cette. Mettant l'accent sur "trucs et astuces", c'est exactement le mauvais chemin à l'approche de la performance. De cette façon conduit à code qui est difficile à comprendre, difficile à comprendre, difficile à maintenir, qui n'est généralement pas sensiblement plus rapide que celle d'un simple code.

Le droit de la démarche de performance est de l'aborder comme un problème d'ingénierie, comme tout autre problème:

  • Ensemble significatifs, mesurables, axés sur le client des objectifs.
  • Générer des suites de test pour tester vos performances par rapport à ces objectifs réalistes mais contrôlé et reproductible conditions.
  • Si ces suites montrer que vous ne remplissez pas vos objectifs, utiliser des outils tels que les profileurs de comprendre pourquoi.
  • Optimiser le diable hors de ce que le générateur de profils identifie comme le pire-l'exécution du sous-système. Garder le profilage à chaque changement, de sorte que vous comprendre clairement l'impact sur les performances de chacun.
  • Répétez jusqu'à ce que l'une des trois choses qui se passe (1), vous atteindre vos objectifs et de les expédier le logiciel, (2) - vous revoir vos objectifs à la baisse pour quelque chose que vous pouvez atteindre, ou (3) votre projet est annulé parce que vous ne pouvait pas répondre à vos objectifs.

C'est la même chose que vous feriez résoudre tout autre problème d'ingénierie, comme l'ajout d'une fonctionnalité -- set axé sur le client des objectifs, de suivre les progrès accomplis sur la réalisation d'une mise en œuvre solide, de résoudre les problèmes que vous trouvez grâce à une analyse de débogage, garder l'itération jusqu'à ce que vous expédier ou à l'échec. La Performance est une fonction.

L'analyse des performances sur les systèmes complexes modernes exige de la discipline et de se concentrer sur de solides principes de l'ingénierie, pas sur un sac plein de trucs qui sont applicables de façon restrictive au trivial ou irréaliste situations. Je n'ai jamais, une fois résolu, dans le monde réel problème de performance grâce à l'application de conseils et d'astuces.

45voto

Reed Copsey Points 315315

Obtenez un bon profileur.

Ne cherchez même pas à optimiser C # (en réalité, n’importe quel code) sans un bon profileur. En fait, il est très utile d’avoir à la fois un profileur d’échantillonnage et un profileur de traçage.

Sans un bon profileur, vous risquez de créer de fausses optimisations et, surtout, d'optimiser les routines qui ne constituent pas un problème de performances.

Les trois premières étapes du profilage doivent toujours être 1) Mesure, 2) Mesure, puis 3) Mesure ....

21voto

Ian Mercer Points 19271

L'optimisation des lignes directrices:

  1. Ne pas le faire sauf si vous avez besoin d'
  2. Ne pas le faire si c'est moins cher de jeter de nouveau matériel sur le problème au lieu d'un développeur
  3. Ne pas le faire, sauf si vous pouvez mesurer les variations de la production de l'équivalent de l'environnement
  4. Ne pas le faire, sauf si vous savez comment utiliser un PROCESSEUR et une Mémoire profiler
  5. Ne le faites pas si ça va rendre votre code illisible ou difficile à maintenir

Comme les processeurs de continuer à obtenir plus rapidement le principal goulet d'étranglement dans la plupart des applications n'est pas la machine, c'est la bande passante: la bande passante pour les hors de la puce de mémoire, la bande passante sur le disque et de bande passante pour net.

Commencer à l'extrême fin: utilisation YSlow pour voir pourquoi votre site web est lent pour les utilisateurs finaux, puis revenir et de vous fixer de base de données accède à ne pas être trop large (colonnes) et pas trop profond (lignes).

Dans les très rares cas où il vaut la peine de faire quelque chose pour optimiser l'utilisation de l'UC être prudent que vous n'êtes pas d'impact négatif sur l'utilisation de la mémoire: j'ai vu des "optimisations" où les développeurs ont essayé d'utiliser la mémoire cache de résultats pour économiser des cycles CPU. L'effet net a été de réduire la mémoire disponible pour mettre en cache les pages et les résultats de base de données qui fait de l'exécution de l'application beaucoup plus lent! (Voir la règle sur la mesure.)

J'ai aussi vu des cas où un "idiot", non optimisée de l'algorithme a battu un "intelligent" algorithme optimisé. Ne jamais sous-estimer la façon dont bon compilateur, les auteurs et les chip-designers sont devenus au tournage de "inefficace" code de boucle en super efficace du code qui peut fonctionner entièrement en mémoire avec le pipelining. Votre "intelligent" de l'arborescence de base de l'algorithme avec une déballé intérieur de la boucle de comptage à rebours que vous avez pensé était "efficace" peut être battu tout simplement car il n'a pas rester en mémoire lors de l'exécution. (Voir la règle sur la mesure.)

16voto

Aaron Points 635

Lorsque vous travaillez avec des ORM, tenez compte des sélections N +1.

 List<Order> _orders = _repository.GetOrders(DateTime.Now);
foreach(var order in _orders)
{
    Print(order.Customer.Name);
}
 

Si les clients ne sont pas chargés avec impatience, cela pourrait entraîner plusieurs allers-retours vers la base de données.

13voto

SoftwareGeek Points 2899
  • N'utilisez pas de nombres magiques, utilisez des énumérations
  • Ne pas coder en dur les valeurs
  • Utilisez des génériques dans la mesure du possible, car il s’agit de typesafe et évite la boxe et le déballage
  • Utilisez le gestionnaire d'erreurs là où c'est absolument nécessaire
  • Dispose, Dispose, Dispose. CLR ne sait pas comment fermer vos connexions à la base de données, alors fermez-les après utilisation et éliminez les ressources non gérées
  • Utiliser le bon sens !

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X