Les performances d’un tri d’array

Le tri d’array permet de réordonner les éléments d’un array en fonction de la valeur d’un élément. On trie en ordre croissant ou décroissant ceci pour rendre plus lisible ces données.

Lorsque un array contient des centaines de milliers d’éléments il est important de comprendre les différentes techniques de triage ainsi on peut optimiser les performances.

Pour les besoins de cet article, créons un array avec 2500 éléments. Pour cela nous créons un object de type PSCustomObject avec un attribut et nous répétons l’opération 2500 fois pour créer l’array:

Maintenant effectuons différents triages en mesurant les performances.

Commençons en utilisant la cmdlet Sort-Object:

Le temps mesuré en secondes est de: 0.1217965

Maintenant au lieu d’utiliser la cmdlet Sort-Object, utilisons la méthode Reverse() de la classe [Array]:

 

Le temps mesuré en secondes est de: 0.0002594

Une énorme différence!

Créons maintenant une collection de type System.Collections.ArrayList. Les collections contrairement aux arrays classiques ont une particularité, elles sont modifiables, alors que les array de type System.array ne le sont pas, on les appelle immuables. Ceci veut dire que pour ajouter un élément à un array on doit en créer un nouveau objet. Alors que pour une collection, on peut allégrement ajouter et enlever des éléments en utilisant toujours le même objet.

Effectuons maintenant un tri et mesurons le temps:

Le temps mesuré en secondes est de: 0.0002459

Encore une amélioration par rapport à [array]::Reverse(), mais pas si significative que ça.

Nous n’avons pas mesuré le temps passé à créer les collections et array. Et la création d’une collection sera toujours plus rapide. Si nous avons des centaines de milliers d’éléments à traiter une collection sera plus rapide qu’un array.

Partager ce contenu

  • Sylvain

    Quelques précisions utiles: la ‘lenteur’ constatée en fait provient principalement de l’usage du pipeline, qui n’est pas multithread. Pour être plus équitable dans la comparaison, il faudrait plutôt mesurer ceci:
    Measure-Command -Expression { Sort-Object -InputObject $array }

    Il en va de même pour Foreach-Object, et toutes autres commandes utilisées fréquemment en conséquence d’un pipeline.

    Pour une idée originale de solution à l’usage du pipeline, cherchez également SplitPipeline sur GitHub (multithread réglable).

    • Merci Sylvain, je vais voir SplitPipeline, en fait il faudrait que je fasse un article entier sur les approches multi-thread, les jobs, les runspaces et quelques outils sympathiques comme Invoke-Parallel. Bonne idée! 🙂