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

SL & STL C++ Discussion :

vector ou list ou map ?


Sujet :

SL & STL C++

  1. #1
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut vector ou list ou map ?
    Salut a tous,

    Dans un de mes projets je ne sais pas si le mieux est d'utiliser des maps, des vectors ou des lists .....

    Voilà ce que j'ai :

    à partir d'un fichier de données, je devrai éxtraire des informations et faire certains traitements dessus pour ensuite les mettres dans une liste, vector, ou map de telle sorte a ne pas avoir le même champs plusieurs fois dans ma liste et ou map.

    le but est de récupérer l'information dans mon fichier de données et de la stocker ensuite dans une map ou liste ou vector ... si cette information existe déja pas la peine de la rajouter et on passe a la ligne suivante du fichier sinon on la rajoute et on lit la seconde ligne ... de telle sorte a la fin a avoir la lsite de ts mes attributs sans avoir de doubles...

    j'ai pensé à utiliser une map pour stocker mes données dans le cas ou ces données n'existent pas .... voici mon code :

    Code : 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
     
     
    map<string, int> ma_map;
     
    while(getline())
    {
    // récupération des données
     
    // je fais les manipulations nécéessaires 
     
    ensuite :
     
    if (!ma_map.find(nom) // si le nom en question de la personne n'est pas trouvée , on le rajoute 
    {
    map[nom] = sonIdentifiant;
    // et la je rajoute mon élément dans la liste et je passe a la ligne suivante
     
    }
     
    sinon je passe a la ligne suivante (une boucle while (getline())
     
     
     
     
    } // fin du While
    est ce que c'est possible aussi de faire un find() sur une map vide ??


    merci pour tous

  2. #2
    Alp
    Alp est déconnecté
    Expert éminent sénior

    Avatar de Alp
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    8 575
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Juin 2005
    Messages : 8 575
    Points : 11 860
    Points
    11 860
    Par défaut
    Tu as regardé le schéma de Laurent Gomila dans la FAQ ?
    http://cpp.developpez.com/faq/cpp/?p...hoix_conteneur

  3. #3
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut
    Oui ... il est bien fait

    Effectivement, dans mon cas le mieux est d'utiliser des maps


    ceci dit ceci ne réponds pas encore a toutes mes questions

    salutation et merci encore ..

  4. #4
    Membre éclairé Avatar de befalimpertinent
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    561
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Gironde (Aquitaine)

    Informations forums :
    Inscription : Avril 2007
    Messages : 561
    Points : 833
    Points
    833
    Par défaut
    Oui tu peux faire un find sur une map vide.
    Par contre find renvoi un iterateur et non un booleen tu dois donc procéder ainsi:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    if (ma_map.find(nom)==ma_map.end())
    {
      //ici l element n'est pas present dans la liste
      map[nom] = sonIdentifiant;
    }
    Mais il est sans doute inutile de rechercher si la personne est présente avant de l'insérer. Tout dépend si tu souhaite garder la premiere occurence d'une personne ou si peut importe (tu écraseras l'identifiant à chaque fois).

    Bref en général ceci suffit:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
      map[nom] = sonIdentifiant;
    Mais il y a un problème dans le choix de ton container : tu peux très bien avoir deux personnes différentes avec le même nom mais pas le meme identifiant non ?
    Dans ce cas penches toi plutôt sur un multimap qui autorise les doublons.
    Mais au vue du nom de tes variables il parait plus logique de faire:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    map<int,string> ma_map;
    Si tes identifiants sont unique à chaque personne (ce qui est généralement le but d'un identifiant)
    Linux > *

  5. #5
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut
    en gros voila ce que j'ai fait :

    Code : 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
     
     
    for(it = map_personne.begin(); it != map_personne.end(); it++ ) // parcourir la map 
    	{  
    	if (it != map_personne.find(nomPersonne)) // si le nomPersonne courant n'est pas déjà dans la map, il le met dans la liste
    				{
     
    				   // map_personne[nomPersonne] = id;
    				// map_personne.insert ( pair<string,int>(nomPersonne,id) );
     
                        ListePersonne.push_back(new Personne(nomPersonne));
    					// dés qu'il trouve il sort de la boucle for et il passe a la lecture de la ligne suivante
     
    				}
     
    				//else
    				//{
    				//	cout << " ne rien faire " << endl; // il passe a la ligne suivante 
    				//}
     
     
    			//}
     
    		} // FIN FOR
     
    			map_personne.insert (it, pair<string,int>(nomPersonne,id)); // je l'insère dans la map (un update) et il passe a la ligne suivante
     
    mais ya comme un pb au niveau de ma boucle car il ne m'affiche pas ce que je veux ... il rentre plusieurs fois dans la boucle !!!

  6. #6
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut
    je retrouve les résultats que je voulais avoir en mettant un break juste avant la fin de la boucle for .... mais si quelqu'un d'autre a une meilleure idée ou une meilleure explication, je suis preneuse.

    merci a vous.

  7. #7
    Membre éclairé Avatar de befalimpertinent
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    561
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Gironde (Aquitaine)

    Informations forums :
    Inscription : Avril 2007
    Messages : 561
    Points : 833
    Points
    833
    Par défaut
    Es tu sur que ta map soit une
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    map<string,int> ma_map;
    //obtenir l'identifiant à partir du nom de la personne
    plutôt que
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    map<int,string> ma_map;
    //obtenir le nom de la personne à partir de l'identifiant - plus logique non ?
    Linux > *

  8. #8
    Membre éclairé Avatar de befalimpertinent
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    561
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Gironde (Aquitaine)

    Informations forums :
    Inscription : Avril 2007
    Messages : 561
    Points : 833
    Points
    833
    Par défaut
    plutot:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    	if (map_personne.end() == map_personne.find(nomPersonne)) 
    // si le nomPersonne courant n'est pas déjà dans la map, il le met dans la liste
    Et pourquoi faire une boucle là où:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    if (map_personne.end() == map_personne.find(nomPersonne))
      {
       ListePersonne.push_back(new Personne(nomPersonne));
      }
    suffit.
    Mais dis nous plutôt clairement ce que tu veux faire parceque là on ceomprend plus ce que viens faire la ListePersonne.
    Linux > *

  9. #9
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut
    Oui alors :

    j'utilise une boucle for pour la simple raison que le nom de la personne est recherché plusieurs fois a chaque lecture d'une ligne de mon fichier.

    en gros : je lis mon fichier,

    je récupère ma donnée ...si elle existe dans ma map alors je passe a la ligne suivante sinon je la récupère dans ma liste...
    je pourrais très bien ne pas mettre de liste de personne c'est juste qu'au début l'idée était d'avoir la liste de personne et la mp vient juste jouer le rôle d'intéermédiaire...
    je pourrais mettre un delete ensuite car de toute facon je ne l'utiliserai pas
    comme je pourrais la garder et manipuler des maps au lieu des listes

  10. #10
    Membre éclairé Avatar de befalimpertinent
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    561
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Gironde (Aquitaine)

    Informations forums :
    Inscription : Avril 2007
    Messages : 561
    Points : 833
    Points
    833
    Par défaut
    Ton premier algo (en apportant quelque corrections) donné dans ton premier post était plus clair.

    Mais je persiste à dire que quelque chose comme cela est suffisant dans ton cas:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    map<string, int> ma_map;
     
    while(getline())
    {
      // récupération des données
      // je fais les manipulations nécéessaires 
     
      ma_map[nom] = sonIdentifiant;
      // si il n'existe pas il sera créé s'il existe déjà il sera ecrase
    }
    Mais que tu te trompe de "sens" (clé - valeur) sur ta map --> utilise soit une multimap soit une map<int,string> (identifiant--> nom de la personne)
    Linux > *

  11. #11
    Débutant(e)
    Inscrit en
    Mars 2006
    Messages
    109
    Détails du profil
    Informations forums :
    Inscription : Mars 2006
    Messages : 109
    Points : 64
    Points
    64
    Par défaut
    le problème c'est que l'identifiant n'est pas un identifiant du nom de la personne proprement dit, je l'ai utilisé car je ne savais pas trop ce que je devais renvoyer a ma valeur string nom ...
    disons c'était juste pour les besoin de la map, j'ai donc utiliser l'identifiant d'un autre attribut d'une autre classe se trouvant dans le même fichier à la lecture.

  12. #12
    Membre éclairé Avatar de befalimpertinent
    Profil pro
    Inscrit en
    Avril 2007
    Messages
    561
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Gironde (Aquitaine)

    Informations forums :
    Inscription : Avril 2007
    Messages : 561
    Points : 833
    Points
    833
    Par défaut
    En fait la question à se poser est :
    "Est ce que nom identifie de manière unique un personne"
    <=>
    "2 personnes peuvent-elles avoir le même nom ?"
    <=>
    "nom peut 'il servir de clé pour une map sans doublon ?"

    Au sens sémantique on voit bien que rien n'empeche 2 personnes de posséder le même nom. Après dans ton contexte particulier... a toi de voir.
    Linux > *

  13. #13
    screetch
    Invité(e)
    Par défaut
    il n'y a jamais besoin de faire un lookup avant d'insérer.

    si il faut remplacer l'élément au cas ou il etait deja la, utiliser []
    si il ne faut pas remplacer, utiliser insert
    insert returne une paire dont le premier membre est l'iterateur destination (mis a jour ou pas) et le second est un booléen indiquant si il y a eu insertion, ou si l'element existait deja (auquel cas il n'a pas ete changé)

    Code : 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
    for(it = map_personne.begin(); it != map_personne.end(); it++ ) // parcourir la map 
    	{  
    	if (map_personne.insert (it, pair<string,int>(nomPersonne,id)).second) // si le nomPersonne courant n'est pas déjà dans la map, il le met dans la liste
    				{
     
    				   // map_personne[nomPersonne] = id;
    				// map_personne.insert ( pair<string,int>(nomPersonne,id) );
     
                        ListePersonne.push_back(new Personne(nomPersonne));
    					// dés qu'il trouve il sort de la boucle for et il passe a la lecture de la ligne suivante
     
    				}
     
    				//else
    				//{
    				//	cout << " ne rien faire " << endl; // il passe a la ligne suivante 
    				//}
     
     
    			//}
     
    		} // FIN FOR

  14. #14
    Expert éminent sénior
    Avatar de Mat.M
    Profil pro
    Développeur informatique
    Inscrit en
    Novembre 2006
    Messages
    8 361
    Détails du profil
    Informations personnelles :
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Novembre 2006
    Messages : 8 361
    Points : 20 381
    Points
    20 381
    Par défaut
    Citation Envoyé par faten7 Voir le message
    Dans un de mes projets je ne sais pas si le mieux est d'utiliser des maps, des vectors ou des lists .....
    Basiquement connais-tu la différence entre ces 3 conteneurs ?
    Un vector c'est un tableau dynamique on peut accéder par indice aux éléments ; un std::list c'est une liste circulaire et un std::map c'est un dictionnaire de données : tu associes une entrée à une clé.
    Citation Envoyé par faten7 Voir le message
    Oui ... il est bien fait

    Effectivement, dans mon cas le mieux est d'utiliser des maps
    .
    Pour quelque chose de plus sophistiqué qui gère personnes il vaut mieux prendre un SGBDR genre Access ou MySQL tu pourras faire des requètes de sélection en SQL ..
    Parce que un std::map dans un projet vraiment professionnel c'est utilisé pour stocker temporairement des infos ou pour des petits ensembles de données

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

    Informations forums :
    Inscription : Juin 2008
    Messages : 3
    Points : 7
    Points
    7
    Par défaut
    Citation Envoyé par Mat.M Voir le message
    un std::list c'est une liste circulaire

    "std::list" c'est une liste doublement chainée

Discussions similaires

  1. JDK 7: Proposition 9 : Notation de tableau pour List et Map -> Intégrée
    Par vbrabant dans le forum Collection et Stream
    Réponses: 58
    Dernier message: 03/09/2009, 15h35
  2. template list pair map
    Par blackfiever dans le forum Langage
    Réponses: 6
    Dernier message: 01/01/2008, 18h25
  3. Optimisation vector ou list
    Par vandamme dans le forum SL & STL
    Réponses: 5
    Dernier message: 02/08/2007, 11h49
  4. récuperer vector dans liste pour combobox
    Par bnreb10 dans le forum Interfaces Graphiques en Java
    Réponses: 33
    Dernier message: 08/08/2006, 10h20
  5. difference entre vector, deque, list et tableau
    Par salseropom dans le forum SL & STL
    Réponses: 8
    Dernier message: 03/01/2005, 13h35

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