IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C# Discussion :

Vaut il mieux utiliser un Dictionary ou une Liste? (Performance)


Sujet :

C#

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éclairé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    284
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 284
    Par défaut Vaut il mieux utiliser un Dictionary ou une Liste? (Performance)
    Bonjour,
    Je me pose une petite question. Je ne sais pas s’il vaut mieux que j’utilise une List<T> ou un Dictionary<int,T>. Je vais vous exposer mon cas.

    Code c# : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
     
    //Mes classes
    public class User
    {
    	public int Id { get; set; }
    	public string Fullname { get; set; }
    	public City City { get; set; }
    }
     
    public class City
    {
    	public int Id { get; set; }
    	public string Type { get; set; }
    }
     
    //Ma méthode côté business
    public void Blablalal()
    {
    	//Cas N°1
    	List<User> userAll = DAL.Manager.GetUser();
    	List<City> cityAll = DAL.Manager.GetCity();
     
    	foreach (var oneUser in userAll)
    		if (oneUser.City != null && oneUser.City.Id > 0)
    			oneUser.City = cityAll.FirstOrDefault(c => c.Id == oneUser.City.Id);
     
     
    	//Cas N°2
    	Dictionary<int,User> userAll = DAL.Manager.GetUser();
    	Dictionary<int,City> cityAll = DAL.Manager.GetCity();
     
    	foreach (var oneUser in userAll.Values)
    		if (oneUser.City != null && oneUser.City.Id > 0)
    			if(cityAll.ContainsKey(oneUser.City.Id))
    				oneUser.City = cityAll[oneUser.City.Id];
     
    }

    La question que je me pose est la suivante. Imaginons un nombre important de villes et de personnes, laquelle des deux méthodes sera la plus rapide d'après vous?
    Merci d'avance pour vos conseils.

  2. #2
    Membre éclairé
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Juin 2005
    Messages
    700
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Tourisme - Loisirs

    Informations forums :
    Inscription : Juin 2005
    Messages : 700
    Par défaut
    il me semble (à confirmer) que si tu as un tres grand nombre d'elements, le dictionnaire deviendra lent que la list (probleme de collision de hashcode).

  3. #3
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    310
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 310
    Par défaut
    +1 pour le List<>.
    De base il est toujours plus rapide de comparer des int que des strings.

  4. #4
    Membre éclairé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    284
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 284
    Par défaut
    Citation Envoyé par jeremm Voir le message
    +1 pour le List<>.
    De base il est toujours plus rapide de comparer des int que des strings.
    Dans mes 2 cas, il y a une comparaison sur un int non?
    Code c# : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    if(cityAll.ContainsKey(oneUser.City.Id))
        oneUser.City = cityAll[oneUser.City.Id];

    C'est marrant, j'aurais dit que c'était le Dictionary le plus rapide.
    Je pensais qu'accéder à un indice était plus rapide que de tout parcourir pour trouver un élément. Mais je ne connais pas le fonctionnement de ContainsKey et je me lance en C#. En tout cas merci pour vos réponses.

  5. #5
    Membre éclairé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    284
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 284
    Par défaut
    Dictionary plus performant?!?!
    Je viens de tomber sur ça C# Dictionary Versus List Lookup Time

  6. #6
    Membre expérimenté Avatar de brachior
    Homme Profil pro
    Doctorant
    Inscrit en
    Mai 2011
    Messages
    190
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Seine et Marne (Île de France)

    Informations professionnelles :
    Activité : Doctorant
    Secteur : Enseignement

    Informations forums :
    Inscription : Mai 2011
    Messages : 190
    Par défaut
    une List et un Dictionary (Table de hachage) sont deux choses bien différentes ...
    Au seul point qu'un Dictinary peut "simuler" une List ...

    ##################################
    Pour une List :
    - L'ajout en fin est en temps constant,
    - L'ajout à un index précis doit l'être aussi (je ne connais pas l'implémentation de C#)

    - La suppression d'un élément est elle en O(N) (où N est le nombre d'élément de la liste)
    - Ou en temps constant si suppression d'un indice.

    - La recherche d'un élément est en O(N) (possibilité d'améliorer par dichotomie si la liste est triée (O(log(N)))
    - Ou en temps constant si demande d'un index

    - Elle garde l'ordre d'entrée

    ##################################
    Pour un Dictionary (Table de hachage)
    - L'ajout, la suppression et la recherche sont en temps constant amorti
    C'est à dire que le temps dépend de la fonction de hachage et de ses probabilités de collisions.

    - Elle ne garde pas l'ordre d'entrée
    - Difficulté pour trier

    ##################################
    En principe, si les éléments doivent rester ordonnés, sont identifiables par un numéro unique et ordonné (0, 1, 2, 3, 4, ...), on préfèrera une liste : accès plus rapide ...

    Si après, l'ordre importe peu, et que les éléments doivent être identifiable de façon plus complexe (id, nom, ...), il est préférable d'utiliser une table de hachage.

    Dans ton exemple, je dirais sans hésiter que le Dictionary ira plus vite à long terme car il ne parcourra jamais la totalité de ta collection, tandis que la liste, si l'élément n'existe pas, elle ne le saura qu'en parcourant la totalité ...


    EDIT :
    Citation Envoyé par giova_fr
    il me semble (à confirmer) que si tu as un tres grand nombre d'elements, le dictionnaire deviendra lent que la list (probleme de collision de hashcode).
    Pour qu'une table de hachage soit plus lent qu'une liste, il faut que ta fonction de hachage soit truquée ...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    public override int GetHashCode()
    {
      return 45;
    }
    Et encore, si la table est à hachage ouvert, alors tu auras la même complexité qu'avec une liste (car tu n'auras en réalité qu'un table d'une liste ^^)

  7. #7
    Membre Expert Avatar de meziantou
    Homme Profil pro
    autre
    Inscrit en
    Avril 2010
    Messages
    1 223
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Autre

    Informations professionnelles :
    Activité : autre
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2010
    Messages : 1 223
    Par défaut
    Un dictionnaire permet de faire une recherche de clé en temps contant (en général). Si la fonction de hash est mal faite, tu peux avoir beaucoup de collisions et dans ce cas tu perds l'intérêt du dictionnaire. Si elle est trop longue à calculer la recherche prendra aussi beaucoup de temps.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    if(cityAll.ContainsKey(oneUser.City.Id))
        oneUser.City = cityAll[oneUser.City.Id];
    Tu peux utiliser la fonction TryGetValue à la place. Ca te fera gagner un peu de temps

    Dans ton cas tu dois pouvoir utiliser une table de hashage à la place d'un dictionnaire.

    Autre solution : faire une liste triée et une recherche dichotomique.

Discussions similaires

  1. Réponses: 12
    Dernier message: 03/07/2009, 13h37
  2. Vaut-il mieux des stock options ou une augmentation de salaire ?
    Par clavier12AZQSWX dans le forum Salaires
    Réponses: 17
    Dernier message: 28/05/2009, 16h10
  3. Utiliser la valeur d'une liste comme paramètre
    Par eudeline91 dans le forum IHM
    Réponses: 0
    Dernier message: 10/06/2008, 11h03
  4. Utilisation de random avec une liste
    Par husobom dans le forum Prolog
    Réponses: 4
    Dernier message: 24/11/2007, 23h43
  5. vaut il mieux utiliser ArrayList ou implémenter collection?
    Par irnbru dans le forum Framework .NET
    Réponses: 17
    Dernier message: 05/11/2005, 12h51

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo